• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1// Copyright 2020 Google Inc. All rights reserved.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7//     http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15package main
16
17import (
18	"bytes"
19	"fmt"
20	"reflect"
21	"testing"
22
23	"google.golang.org/protobuf/encoding/prototext"
24
25	bp "android/soong/cmd/extract_apks/bundle_proto"
26	"android/soong/third_party/zip"
27)
28
29type testConfigDesc struct {
30	name         string
31	targetConfig TargetConfig
32	expected     SelectionResult
33}
34
35type testDesc struct {
36	protoText string
37	configs   []testConfigDesc
38}
39
40func TestSelectApks_ApkSet(t *testing.T) {
41	testCases := []testDesc{
42		{
43			protoText: `
44variant {
45  targeting {
46    sdk_version_targeting {
47      value { min { value: 29 } } } }
48  apk_set {
49    module_metadata {
50      name: "base" targeting {} delivery_type: INSTALL_TIME }
51    apk_description {
52      targeting {
53        screen_density_targeting {
54          value { density_alias: LDPI } }
55        sdk_version_targeting {
56          value { min { value: 21 } } } }
57      path: "splits/base-ldpi.apk"
58      split_apk_metadata { split_id: "config.ldpi" } }
59    apk_description {
60      targeting {
61        screen_density_targeting {
62          value { density_alias: MDPI } }
63        sdk_version_targeting {
64          value { min { value: 21 } } } }
65      path: "splits/base-mdpi.apk"
66      split_apk_metadata { split_id: "config.mdpi" } }
67    apk_description {
68      targeting {
69        sdk_version_targeting {
70          value { min { value: 21 } } } }
71      path: "splits/base-master.apk"
72      split_apk_metadata { is_master_split: true } }
73    apk_description {
74      targeting {
75        abi_targeting {
76          value { alias: ARMEABI_V7A }
77          alternatives { alias: ARM64_V8A }
78          alternatives { alias: X86 }
79          alternatives { alias: X86_64 } }
80        sdk_version_targeting {
81          value { min { value: 21 } } } }
82      path: "splits/base-armeabi_v7a.apk"
83      split_apk_metadata { split_id: "config.armeabi_v7a" } }
84    apk_description {
85      targeting {
86        abi_targeting {
87          value { alias: ARM64_V8A }
88          alternatives { alias: ARMEABI_V7A }
89          alternatives { alias: X86 }
90          alternatives { alias: X86_64 } }
91        sdk_version_targeting {
92          value { min { value: 21 } } } }
93      path: "splits/base-arm64_v8a.apk"
94      split_apk_metadata { split_id: "config.arm64_v8a" } }
95    apk_description {
96      targeting {
97        abi_targeting {
98          value { alias: X86 }
99          alternatives { alias: ARMEABI_V7A }
100          alternatives { alias: ARM64_V8A }
101          alternatives { alias: X86_64 } }
102        sdk_version_targeting {
103          value { min { value: 21 } } } }
104      path: "splits/base-x86.apk"
105      split_apk_metadata { split_id: "config.x86" } }
106    apk_description {
107      targeting {
108        abi_targeting {
109          value { alias: X86_64 }
110          alternatives { alias: ARMEABI_V7A }
111          alternatives { alias: ARM64_V8A }
112          alternatives { alias: X86 } }
113        sdk_version_targeting {
114          value { min { value: 21 } } } }
115      path: "splits/base-x86_64.apk"
116      split_apk_metadata { split_id: "config.x86_64" } } }
117}
118bundletool {
119  version: "0.10.3" }
120
121`,
122			configs: []testConfigDesc{
123				{
124					name: "one",
125					targetConfig: TargetConfig{
126						sdkVersion: 29,
127						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
128							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
129						},
130						abis: map[bp.Abi_AbiAlias]int{
131							bp.Abi_ARMEABI_V7A: 0,
132							bp.Abi_ARM64_V8A:   1,
133						},
134					},
135					expected: SelectionResult{
136						"base",
137						[]string{
138							"splits/base-ldpi.apk",
139							"splits/base-mdpi.apk",
140							"splits/base-master.apk",
141							"splits/base-armeabi_v7a.apk",
142						},
143					},
144				},
145				{
146					name: "two",
147					targetConfig: TargetConfig{
148						sdkVersion: 29,
149						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
150							bp.ScreenDensity_LDPI: true,
151						},
152						abis: map[bp.Abi_AbiAlias]int{},
153					},
154					expected: SelectionResult{
155						"base",
156						[]string{
157							"splits/base-ldpi.apk",
158							"splits/base-master.apk",
159						},
160					},
161				},
162				{
163					name: "three",
164					targetConfig: TargetConfig{
165						sdkVersion: 20,
166						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
167							bp.ScreenDensity_LDPI: true,
168						},
169						abis: map[bp.Abi_AbiAlias]int{},
170					},
171					expected: SelectionResult{
172						"",
173						nil,
174					},
175				},
176				{
177					name: "four",
178					targetConfig: TargetConfig{
179						sdkVersion: 29,
180						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
181							bp.ScreenDensity_MDPI: true,
182						},
183						abis: map[bp.Abi_AbiAlias]int{
184							bp.Abi_ARM64_V8A:   0,
185							bp.Abi_ARMEABI_V7A: 1,
186						},
187					},
188					expected: SelectionResult{
189						"base",
190						[]string{
191							"splits/base-mdpi.apk",
192							"splits/base-master.apk",
193							"splits/base-arm64_v8a.apk",
194						},
195					},
196				},
197			},
198		},
199		{
200			protoText: `
201variant {
202  targeting {
203    sdk_version_targeting {
204      value { min { value: 10000 } } } }
205  apk_set {
206    module_metadata {
207      name: "base" targeting {} delivery_type: INSTALL_TIME }
208    apk_description {
209      targeting {
210        sdk_version_targeting {
211          value { min { value: 21 } } } }
212      path: "splits/base-master.apk"
213      split_apk_metadata { is_master_split: true } } } }`,
214			configs: []testConfigDesc{
215				{
216					name: "Prerelease",
217					targetConfig: TargetConfig{
218						sdkVersion:       30,
219						screenDpi:        map[bp.ScreenDensity_DensityAlias]bool{},
220						abis:             map[bp.Abi_AbiAlias]int{},
221						allowPrereleased: true,
222					},
223					expected: SelectionResult{
224						"base",
225						[]string{"splits/base-master.apk"},
226					},
227				},
228			},
229		},
230		{
231			protoText: `
232variant {
233  targeting {
234    sdk_version_targeting {
235      value { min { value: 29 } } } }
236  apk_set {
237    module_metadata {
238      name: "base" targeting {} delivery_type: INSTALL_TIME }
239    apk_description {
240      targeting {}
241      path: "universal.apk"
242      standalone_apk_metadata { fused_module_name: "base" } } } }`,
243			configs: []testConfigDesc{
244				{
245					name:         "Universal",
246					targetConfig: TargetConfig{sdkVersion: 30},
247					expected: SelectionResult{
248						"base",
249						[]string{"universal.apk"},
250					},
251				},
252			},
253		},
254	}
255	for _, testCase := range testCases {
256		var toc bp.BuildApksResult
257		if err := prototext.Unmarshal([]byte(testCase.protoText), &toc); err != nil {
258			t.Fatal(err)
259		}
260		for _, config := range testCase.configs {
261			actual := selectApks(&toc, config.targetConfig)
262			if !reflect.DeepEqual(config.expected, actual) {
263				t.Errorf("%s: expected %v, got %v", config.name, config.expected, actual)
264			}
265		}
266	}
267}
268
269func TestSelectApks_ApexSet(t *testing.T) {
270	testCases := []testDesc{
271		{
272			protoText: `
273variant {
274  targeting {
275    sdk_version_targeting {
276      value { min { value: 29 } } } }
277  apk_set {
278    module_metadata {
279      name: "base" targeting {} delivery_type: INSTALL_TIME }
280    apk_description {
281      targeting {
282        multi_abi_targeting {
283          value { abi { alias: ARMEABI_V7A } }
284          alternatives { abi { alias: ARM64_V8A } }
285          alternatives { abi { alias: X86 } }
286          alternatives { abi { alias: X86_64 } } }
287        sdk_version_targeting {
288          value { min { value: 21 } } } }
289      path: "standalones/standalone-armeabi_v7a.apex"
290      apex_apk_metadata { } }
291    apk_description {
292      targeting {
293        multi_abi_targeting {
294          value { abi { alias: ARM64_V8A } }
295          alternatives { abi { alias: ARMEABI_V7A } }
296          alternatives { abi { alias: X86 } }
297          alternatives { abi { alias: X86_64 } } }
298        sdk_version_targeting {
299          value { min { value: 21 } } } }
300      path: "standalones/standalone-arm64_v8a.apex"
301      apex_apk_metadata { } }
302    apk_description {
303      targeting {
304        multi_abi_targeting {
305          value { abi { alias: X86 } }
306          alternatives { abi { alias: ARMEABI_V7A } }
307          alternatives { abi { alias: ARM64_V8A } }
308          alternatives { abi { alias: X86_64 } } }
309        sdk_version_targeting {
310          value { min { value: 21 } } } }
311      path: "standalones/standalone-x86.apex"
312      apex_apk_metadata { } }
313    apk_description {
314      targeting {
315        multi_abi_targeting {
316          value { abi { alias: X86_64 } }
317          alternatives { abi { alias: ARMEABI_V7A } }
318          alternatives { abi { alias: ARM64_V8A } }
319          alternatives { abi { alias: X86 } } }
320        sdk_version_targeting {
321          value { min { value: 21 } } } }
322      path: "standalones/standalone-x86_64.apex"
323      apex_apk_metadata { } } }
324}
325bundletool {
326  version: "0.10.3" }
327
328`,
329			configs: []testConfigDesc{
330				{
331					name: "order matches priorities",
332					targetConfig: TargetConfig{
333						sdkVersion: 29,
334						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
335							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
336						},
337						abis: map[bp.Abi_AbiAlias]int{
338							bp.Abi_ARM64_V8A:   0,
339							bp.Abi_ARMEABI_V7A: 1,
340						},
341					},
342					expected: SelectionResult{
343						"base",
344						[]string{
345							"standalones/standalone-arm64_v8a.apex",
346						},
347					},
348				},
349				{
350					name: "order doesn't match priorities",
351					targetConfig: TargetConfig{
352						sdkVersion: 29,
353						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
354							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
355						},
356						abis: map[bp.Abi_AbiAlias]int{
357							bp.Abi_ARMEABI_V7A: 0,
358							bp.Abi_ARM64_V8A:   1,
359						},
360					},
361					expected: SelectionResult{
362						"base",
363						[]string{
364							"standalones/standalone-arm64_v8a.apex",
365						},
366					},
367				},
368				{
369					name: "single choice",
370					targetConfig: TargetConfig{
371						sdkVersion: 29,
372						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
373							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
374						},
375						abis: map[bp.Abi_AbiAlias]int{
376							bp.Abi_ARMEABI_V7A: 0,
377						},
378					},
379					expected: SelectionResult{
380						"base",
381						[]string{
382							"standalones/standalone-armeabi_v7a.apex",
383						},
384					},
385				},
386				{
387					name: "cross platform",
388					targetConfig: TargetConfig{
389						sdkVersion: 29,
390						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
391							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
392						},
393						abis: map[bp.Abi_AbiAlias]int{
394							bp.Abi_ARM64_V8A: 0,
395							bp.Abi_MIPS64:    1,
396							bp.Abi_X86:       2,
397						},
398					},
399					expected: SelectionResult{
400						"base",
401						[]string{
402							"standalones/standalone-x86.apex",
403						},
404					},
405				},
406			},
407		},
408	}
409	for _, testCase := range testCases {
410		var toc bp.BuildApksResult
411		if err := prototext.Unmarshal([]byte(testCase.protoText), &toc); err != nil {
412			t.Fatal(err)
413		}
414		for _, config := range testCase.configs {
415			actual := selectApks(&toc, config.targetConfig)
416			if !reflect.DeepEqual(config.expected, actual) {
417				t.Errorf("%s: expected %v, got %v", config.name, config.expected, actual)
418			}
419		}
420	}
421}
422
423func TestSelectApks_ApexSet_Variants(t *testing.T) {
424	testCases := []testDesc{
425		{
426			protoText: `
427variant {
428	targeting {
429		sdk_version_targeting {value {min {value: 29}}}
430		multi_abi_targeting {
431			value {abi {alias: ARMEABI_V7A}}
432			alternatives {
433				abi {alias: ARMEABI_V7A}
434				abi {alias: ARM64_V8A}
435			}
436			alternatives {abi {alias: ARM64_V8A}}
437			alternatives {abi {alias: X86}}
438			alternatives {
439				abi {alias: X86}
440				abi {alias: X86_64}
441			}
442		}
443	}
444	apk_set {
445		module_metadata {
446			name: "base"
447			delivery_type: INSTALL_TIME
448		}
449		apk_description {
450			targeting {
451				multi_abi_targeting {
452					value {abi {alias: ARMEABI_V7A}}
453					alternatives {
454						abi {alias: ARMEABI_V7A}
455						abi {alias: ARM64_V8A}
456					}
457					alternatives {abi {alias: ARM64_V8A}}
458					alternatives {abi {alias: X86}}
459					alternatives {
460						abi {alias: X86}
461						abi {alias: X86_64}
462					}
463				}
464			}
465			path: "standalones/standalone-armeabi_v7a.apex"
466		}
467	}
468	variant_number: 0
469}
470variant {
471	targeting {
472		sdk_version_targeting {value {min {value: 29}}}
473		multi_abi_targeting {
474			value {abi {alias: ARM64_V8A}}
475			alternatives {abi {alias: ARMEABI_V7A}}
476			alternatives {
477				abi {alias: ARMEABI_V7A}
478				abi {alias: ARM64_V8A}
479			}
480			alternatives {abi {alias: X86}}
481			alternatives {
482				abi {alias: X86}
483				abi {alias: X86_64}
484			}
485		}
486	}
487	apk_set {
488		module_metadata {
489			name: "base"
490			delivery_type: INSTALL_TIME
491		}
492		apk_description {
493			targeting {
494				multi_abi_targeting {
495					value {abi {alias: ARM64_V8A}}
496					alternatives {abi {alias: ARMEABI_V7A}}
497					alternatives {
498						abi {alias: ARMEABI_V7A}
499						abi {alias: ARM64_V8A}
500					}
501					alternatives {abi {alias: X86}}
502					alternatives {
503						abi {alias: X86}
504						abi {alias: X86_64}
505					}
506				}
507			}
508			path: "standalones/standalone-arm64_v8a.apex"
509		}
510	}
511	variant_number: 1
512}
513variant {
514	targeting {
515		sdk_version_targeting {value {min {value: 29}}}
516		multi_abi_targeting {
517			value {
518				abi {alias: ARMEABI_V7A}
519				abi {alias: ARM64_V8A}
520			}
521			alternatives {abi {alias: ARMEABI_V7A}}
522			alternatives {abi {alias: ARM64_V8A}}
523			alternatives {abi {alias: X86}}
524			alternatives {
525				abi {alias: X86}
526				abi {alias: X86_64}
527			}
528		}
529	}
530	apk_set {
531		module_metadata {
532			name: "base"
533			delivery_type: INSTALL_TIME
534		}
535		apk_description {
536			targeting {
537				multi_abi_targeting {
538					value {
539						abi {alias: ARMEABI_V7A}
540						abi {alias: ARM64_V8A}
541					}
542					alternatives {abi {alias: ARMEABI_V7A}}
543					alternatives {abi {alias: ARM64_V8A}}
544					alternatives {abi {alias: X86}}
545					alternatives {
546						abi {alias: X86}
547						abi {alias: X86_64}
548					}
549				}
550			}
551			path: "standalones/standalone-armeabi_v7a.arm64_v8a.apex"
552		}
553	}
554	variant_number: 2
555}
556variant {
557	targeting {
558		sdk_version_targeting {value {min {value: 29}}}
559		multi_abi_targeting {
560			value {abi {alias: X86}}
561			alternatives {abi {alias: ARMEABI_V7A}}
562			alternatives {
563				abi {alias: ARMEABI_V7A}
564				abi {alias: ARM64_V8A}
565			}
566			alternatives {abi {alias: ARM64_V8A}}
567			alternatives {
568				abi {alias: X86}
569				abi {alias: X86_64}
570			}
571		}
572	}
573	apk_set {
574		module_metadata {
575			name: "base"
576			delivery_type: INSTALL_TIME
577		}
578		apk_description {
579			targeting {
580				multi_abi_targeting {
581					value {abi {alias: X86}}
582					alternatives {abi {alias: ARMEABI_V7A}}
583					alternatives {
584						abi {alias: ARMEABI_V7A}
585						abi {alias: ARM64_V8A}
586					}
587					alternatives {abi {alias: ARM64_V8A}}
588					alternatives {
589						abi {alias: X86}
590						abi {alias: X86_64}
591					}
592				}
593			}
594			path: "standalones/standalone-x86.apex"
595		}
596	}
597	variant_number: 3
598}
599variant {
600	targeting {
601		sdk_version_targeting {value {min {value: 29}}}
602		multi_abi_targeting {
603			value {
604				abi {alias: X86}
605				abi {alias: X86_64}
606			}
607			alternatives {abi {alias: ARMEABI_V7A}}
608			alternatives {
609				abi {alias: ARMEABI_V7A}
610				abi {alias: ARM64_V8A}
611			}
612			alternatives {abi {alias: ARM64_V8A}}
613			alternatives {abi {alias: X86}}
614		}
615	}
616	apk_set {
617		module_metadata {
618			name: "base"
619			delivery_type: INSTALL_TIME
620		}
621		apk_description {
622			targeting {
623				multi_abi_targeting {
624					value {
625						abi {alias: X86}
626						abi {alias: X86_64}
627					}
628					alternatives {abi {alias: ARMEABI_V7A}}
629					alternatives {
630						abi {alias: ARMEABI_V7A}
631						abi {alias: ARM64_V8A}
632					}
633					alternatives {abi {alias: ARM64_V8A}}
634					alternatives {abi {alias: X86}}
635				}
636			}
637			path: "standalones/standalone-x86.x86_64.apex"
638		}
639  }
640  variant_number: 4
641}
642`,
643			configs: []testConfigDesc{
644				{
645					name: "multi-variant multi-target ARM",
646					targetConfig: TargetConfig{
647						sdkVersion: 33,
648						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
649							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
650						},
651						abis: map[bp.Abi_AbiAlias]int{
652							bp.Abi_ARM64_V8A:   0,
653							bp.Abi_ARMEABI_V7A: 1,
654						},
655					},
656					expected: SelectionResult{
657						"base",
658						[]string{
659							"standalones/standalone-armeabi_v7a.arm64_v8a.apex",
660						},
661					},
662				},
663				{
664					name: "multi-variant single-target arm",
665					targetConfig: TargetConfig{
666						sdkVersion: 33,
667						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
668							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
669						},
670						abis: map[bp.Abi_AbiAlias]int{
671							bp.Abi_ARMEABI_V7A: 0,
672						},
673					},
674					expected: SelectionResult{
675						"base",
676						[]string{
677							"standalones/standalone-armeabi_v7a.apex",
678						},
679					},
680				},
681				{
682					name: "multi-variant single-target arm64",
683					targetConfig: TargetConfig{
684						sdkVersion: 33,
685						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
686							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
687						},
688						abis: map[bp.Abi_AbiAlias]int{
689							bp.Abi_ARM64_V8A: 0,
690						},
691					},
692					expected: SelectionResult{
693						"base",
694						[]string{
695							"standalones/standalone-arm64_v8a.apex",
696						},
697					},
698				},
699				{
700					name: "multi-variant multi-target x86",
701					targetConfig: TargetConfig{
702						sdkVersion: 33,
703						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
704							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
705						},
706						abis: map[bp.Abi_AbiAlias]int{
707							bp.Abi_X86:    0,
708							bp.Abi_X86_64: 1,
709						},
710					},
711					expected: SelectionResult{
712						"base",
713						[]string{
714							"standalones/standalone-x86.x86_64.apex",
715						},
716					},
717				},
718				{
719					name: "multi-variant single-target x86",
720					targetConfig: TargetConfig{
721						sdkVersion: 33,
722						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
723							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
724						},
725						abis: map[bp.Abi_AbiAlias]int{
726							bp.Abi_X86: 0,
727						},
728					},
729					expected: SelectionResult{
730						"base",
731						[]string{
732							"standalones/standalone-x86.apex",
733						},
734					},
735				},
736				{
737					name: "multi-variant single-target x86_64",
738					targetConfig: TargetConfig{
739						sdkVersion: 33,
740						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
741							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
742						},
743						abis: map[bp.Abi_AbiAlias]int{
744							bp.Abi_X86_64: 0,
745						},
746					},
747					expected: SelectionResult{
748						"base",
749						[]string{
750							"standalones/standalone-x86.x86_64.apex",
751						}},
752				},
753				{
754					name: "multi-variant multi-target cross-target",
755					targetConfig: TargetConfig{
756						sdkVersion: 33,
757						screenDpi: map[bp.ScreenDensity_DensityAlias]bool{
758							bp.ScreenDensity_DENSITY_UNSPECIFIED: true,
759						},
760						abis: map[bp.Abi_AbiAlias]int{
761							bp.Abi_ARM64_V8A: 0,
762							bp.Abi_X86_64:    1,
763						},
764					},
765					expected: SelectionResult{
766						"base",
767						[]string{
768							"standalones/standalone-arm64_v8a.apex",
769						},
770					},
771				},
772			},
773		},
774	}
775	for _, testCase := range testCases {
776		var toc bp.BuildApksResult
777		if err := prototext.Unmarshal([]byte(testCase.protoText), &toc); err != nil {
778			t.Fatal(err)
779		}
780		for _, config := range testCase.configs {
781			t.Run(config.name, func(t *testing.T) {
782				actual := selectApks(&toc, config.targetConfig)
783				if !reflect.DeepEqual(config.expected, actual) {
784					t.Errorf("expected %v, got %v", config.expected, actual)
785				}
786			})
787		}
788	}
789}
790
791type testZip2ZipWriter struct {
792	entries map[string]string
793}
794
795func (w testZip2ZipWriter) CopyFrom(file *zip.File, out string) error {
796	if x, ok := w.entries[out]; ok {
797		return fmt.Errorf("%s and %s both write to %s", x, file.Name, out)
798	}
799	w.entries[out] = file.Name
800	return nil
801}
802
803type testCaseWriteApks struct {
804	name       string
805	moduleName string
806	stem       string
807	partition  string
808	// what we write from what
809	zipEntries       map[string]string
810	expectedApkcerts []string
811}
812
813func TestWriteApks(t *testing.T) {
814	testCases := []testCaseWriteApks{
815		{
816			name:       "splits",
817			moduleName: "mybase",
818			stem:       "Foo",
819			partition:  "system",
820			zipEntries: map[string]string{
821				"Foo.apk":       "splits/mybase-master.apk",
822				"Foo-xhdpi.apk": "splits/mybase-xhdpi.apk",
823			},
824			expectedApkcerts: []string{
825				`name="Foo-xhdpi.apk" certificate="PRESIGNED" private_key="" partition="system"`,
826				`name="Foo.apk" certificate="PRESIGNED" private_key="" partition="system"`,
827			},
828		},
829		{
830			name:       "universal",
831			moduleName: "base",
832			stem:       "Bar",
833			partition:  "product",
834			zipEntries: map[string]string{
835				"Bar.apk": "universal.apk",
836			},
837			expectedApkcerts: []string{
838				`name="Bar.apk" certificate="PRESIGNED" private_key="" partition="product"`,
839			},
840		},
841	}
842	for _, testCase := range testCases {
843		t.Run(testCase.name, func(t *testing.T) {
844			testZipBuf := &bytes.Buffer{}
845			testZip := zip.NewWriter(testZipBuf)
846			for _, in := range testCase.zipEntries {
847				f, _ := testZip.Create(in)
848				f.Write([]byte(in))
849			}
850			testZip.Close()
851
852			zipReader, _ := zip.NewReader(bytes.NewReader(testZipBuf.Bytes()), int64(testZipBuf.Len()))
853
854			apkSet := ApkSet{entries: make(map[string]*zip.File)}
855			sel := SelectionResult{moduleName: testCase.moduleName}
856			for _, f := range zipReader.File {
857				apkSet.entries[f.Name] = f
858				sel.entries = append(sel.entries, f.Name)
859			}
860
861			zipWriter := testZip2ZipWriter{make(map[string]string)}
862			outWriter := &bytes.Buffer{}
863			config := TargetConfig{stem: testCase.stem}
864			apkcerts, err := apkSet.writeApks(sel, config, outWriter, zipWriter, testCase.partition)
865			if err != nil {
866				t.Error(err)
867			}
868			expectedZipEntries := make(map[string]string)
869			for k, v := range testCase.zipEntries {
870				if k != testCase.stem+".apk" {
871					expectedZipEntries[k] = v
872				}
873			}
874			if !reflect.DeepEqual(expectedZipEntries, zipWriter.entries) {
875				t.Errorf("expected zip entries %v, got %v", testCase.zipEntries, zipWriter.entries)
876			}
877			if !reflect.DeepEqual(testCase.expectedApkcerts, apkcerts) {
878				t.Errorf("expected apkcerts %v, got %v", testCase.expectedApkcerts, apkcerts)
879			}
880			if g, w := outWriter.String(), testCase.zipEntries[testCase.stem+".apk"]; !reflect.DeepEqual(g, w) {
881				t.Errorf("expected output file contents %q, got %q", testCase.stem+".apk", outWriter.String())
882			}
883		})
884	}
885}
886