diff --git a/cmd/soong_build/Android.bp b/cmd/soong_build/Android.bp
index 441ea0d..6714978 100644
--- a/cmd/soong_build/Android.bp
+++ b/cmd/soong_build/Android.bp
@@ -20,6 +20,7 @@
         "golang-protobuf-proto",
         "soong",
         "soong-android",
+        "soong-bp2build",
         "soong-env",
         "soong-ui-metrics_proto",
     ],
@@ -27,10 +28,6 @@
         "main.go",
         "writedocs.go",
         "queryview.go",
-        "queryview_templates.go",
-    ],
-    testSrcs: [
-        "queryview_test.go",
     ],
     primaryBuilder: true,
 }
diff --git a/cmd/soong_build/queryview.go b/cmd/soong_build/queryview.go
index f5aa685..3657ea8 100644
--- a/cmd/soong_build/queryview.go
+++ b/cmd/soong_build/queryview.go
@@ -16,512 +16,82 @@
 
 import (
 	"android/soong/android"
-	"fmt"
+	"android/soong/bp2build"
 	"io/ioutil"
 	"os"
 	"path/filepath"
-	"reflect"
-	"strings"
 
 	"github.com/google/blueprint"
-	"github.com/google/blueprint/bootstrap/bpdoc"
-	"github.com/google/blueprint/proptools"
 )
 
-var (
-	// An allowlist of prop types that are surfaced from module props to rule
-	// attributes. (nested) dictionaries are notably absent here, because while
-	// Soong supports multi value typed and nested dictionaries, Bazel's rule
-	// attr() API supports only single-level string_dicts.
-	allowedPropTypes = map[string]bool{
-		"int":         true, // e.g. 42
-		"bool":        true, // e.g. True
-		"string_list": true, // e.g. ["a", "b"]
-		"string":      true, // e.g. "a"
-	}
-
-	// Certain module property names are blocklisted/ignored here, for the reasons commented.
-	ignoredPropNames = map[string]bool{
-		"name":       true, // redundant, since this is explicitly generated for every target
-		"from":       true, // reserved keyword
-		"in":         true, // reserved keyword
-		"arch":       true, // interface prop type is not supported yet.
-		"multilib":   true, // interface prop type is not supported yet.
-		"target":     true, // interface prop type is not supported yet.
-		"visibility": true, // Bazel has native visibility semantics. Handle later.
-		"features":   true, // There is already a built-in attribute 'features' which cannot be overridden.
-	}
-)
-
-func targetNameWithVariant(c *blueprint.Context, logicModule blueprint.Module) string {
-	name := ""
-	if c.ModuleSubDir(logicModule) != "" {
-		// TODO(b/162720883): Figure out a way to drop the "--" variant suffixes.
-		name = c.ModuleName(logicModule) + "--" + c.ModuleSubDir(logicModule)
-	} else {
-		name = c.ModuleName(logicModule)
-	}
-
-	return strings.Replace(name, "//", "", 1)
+type queryviewContext struct {
+	bpCtx *blueprint.Context
 }
 
-func qualifiedTargetLabel(c *blueprint.Context, logicModule blueprint.Module) string {
-	return "//" +
-		packagePath(c, logicModule) +
-		":" +
-		targetNameWithVariant(c, logicModule)
+func (ctx *queryviewContext) ModuleName(module blueprint.Module) string {
+	return ctx.bpCtx.ModuleName(module)
 }
 
-func packagePath(c *blueprint.Context, logicModule blueprint.Module) string {
-	return filepath.Dir(c.BlueprintFile(logicModule))
+func (ctx *queryviewContext) ModuleDir(module blueprint.Module) string {
+	return ctx.bpCtx.ModuleDir(module)
 }
 
-func escapeString(s string) string {
-	s = strings.ReplaceAll(s, "\\", "\\\\")
-	return strings.ReplaceAll(s, "\"", "\\\"")
+func (ctx *queryviewContext) ModuleSubDir(module blueprint.Module) string {
+	return ctx.bpCtx.ModuleSubDir(module)
 }
 
-func makeIndent(indent int) string {
-	if indent < 0 {
-		panic(fmt.Errorf("indent column cannot be less than 0, but got %d", indent))
-	}
-	return strings.Repeat("    ", indent)
+func (ctx *queryviewContext) ModuleType(module blueprint.Module) string {
+	return ctx.bpCtx.ModuleType(module)
 }
 
-// prettyPrint a property value into the equivalent Starlark representation
-// recursively.
-func prettyPrint(propertyValue reflect.Value, indent int) (string, error) {
-	if isZero(propertyValue) {
-		// A property value being set or unset actually matters -- Soong does set default
-		// values for unset properties, like system_shared_libs = ["libc", "libm", "libdl"] at
-		// https://cs.android.com/android/platform/superproject/+/master:build/soong/cc/linker.go;l=281-287;drc=f70926eef0b9b57faf04c17a1062ce50d209e480
-		//
-		// In Bazel-parlance, we would use "attr.<type>(default = <default value>)" to set the default
-		// value of unset attributes.
-		return "", nil
-	}
-
-	var ret string
-	switch propertyValue.Kind() {
-	case reflect.String:
-		ret = fmt.Sprintf("\"%v\"", escapeString(propertyValue.String()))
-	case reflect.Bool:
-		ret = strings.Title(fmt.Sprintf("%v", propertyValue.Interface()))
-	case reflect.Int, reflect.Uint, reflect.Int64:
-		ret = fmt.Sprintf("%v", propertyValue.Interface())
-	case reflect.Ptr:
-		return prettyPrint(propertyValue.Elem(), indent)
-	case reflect.Slice:
-		ret = "[\n"
-		for i := 0; i < propertyValue.Len(); i++ {
-			indexedValue, err := prettyPrint(propertyValue.Index(i), indent+1)
-			if err != nil {
-				return "", err
-			}
-
-			if indexedValue != "" {
-				ret += makeIndent(indent + 1)
-				ret += indexedValue
-				ret += ",\n"
-			}
-		}
-		ret += makeIndent(indent)
-		ret += "]"
-	case reflect.Struct:
-		ret = "{\n"
-		// Sort and print the struct props by the key.
-		structProps := extractStructProperties(propertyValue, indent)
-		for _, k := range android.SortedStringKeys(structProps) {
-			ret += makeIndent(indent + 1)
-			ret += fmt.Sprintf("%q: %s,\n", k, structProps[k])
-		}
-		ret += makeIndent(indent)
-		ret += "}"
-	case reflect.Interface:
-		// TODO(b/164227191): implement pretty print for interfaces.
-		// Interfaces are used for for arch, multilib and target properties.
-		return "", nil
-	default:
-		return "", fmt.Errorf(
-			"unexpected kind for property struct field: %s", propertyValue.Kind())
-	}
-	return ret, nil
+func (ctx *queryviewContext) VisitAllModulesBlueprint(visit func(blueprint.Module)) {
+	ctx.bpCtx.VisitAllModules(visit)
 }
 
-// Converts a reflected property struct value into a map of property names and property values,
-// which each property value correctly pretty-printed and indented at the right nest level,
-// since property structs can be nested. In Starlark, nested structs are represented as nested
-// dicts: https://docs.bazel.build/skylark/lib/dict.html
-func extractStructProperties(structValue reflect.Value, indent int) map[string]string {
-	if structValue.Kind() != reflect.Struct {
-		panic(fmt.Errorf("Expected a reflect.Struct type, but got %s", structValue.Kind()))
-	}
-
-	ret := map[string]string{}
-	structType := structValue.Type()
-	for i := 0; i < structValue.NumField(); i++ {
-		field := structType.Field(i)
-		if field.PkgPath != "" {
-			// Skip unexported fields. Some properties are
-			// internal to Soong only, and these fields do not have PkgPath.
-			continue
+func (ctx *queryviewContext) VisitDirectDeps(module android.Module, visit func(android.Module)) {
+	ctx.bpCtx.VisitDirectDeps(module, func(m blueprint.Module) {
+		if aModule, ok := m.(android.Module); ok {
+			visit(aModule)
 		}
-		if proptools.HasTag(field, "blueprint", "mutated") {
-			continue
-		}
-
-		fieldValue := structValue.Field(i)
-		if isZero(fieldValue) {
-			// Ignore zero-valued fields
-			continue
-		}
-
-		propertyName := proptools.PropertyNameForField(field.Name)
-		prettyPrintedValue, err := prettyPrint(fieldValue, indent+1)
-		if err != nil {
-			panic(
-				fmt.Errorf(
-					"Error while parsing property: %q. %s",
-					propertyName,
-					err))
-		}
-		if prettyPrintedValue != "" {
-			ret[propertyName] = prettyPrintedValue
-		}
-	}
-
-	return ret
-}
-
-func isStructPtr(t reflect.Type) bool {
-	return t.Kind() == reflect.Ptr && t.Elem().Kind() == reflect.Struct
-}
-
-// Generically extract module properties and types into a map, keyed by the module property name.
-func extractModuleProperties(aModule android.Module) map[string]string {
-	ret := map[string]string{}
-
-	// Iterate over this android.Module's property structs.
-	for _, properties := range aModule.GetProperties() {
-		propertiesValue := reflect.ValueOf(properties)
-		// Check that propertiesValue is a pointer to the Properties struct, like
-		// *cc.BaseLinkerProperties or *java.CompilerProperties.
-		//
-		// propertiesValue can also be type-asserted to the structs to
-		// manipulate internal props, if needed.
-		if isStructPtr(propertiesValue.Type()) {
-			structValue := propertiesValue.Elem()
-			for k, v := range extractStructProperties(structValue, 0) {
-				ret[k] = v
-			}
-		} else {
-			panic(fmt.Errorf(
-				"properties must be a pointer to a struct, got %T",
-				propertiesValue.Interface()))
-		}
-
-	}
-
-	return ret
-}
-
-// FIXME(b/168089390): In Bazel, rules ending with "_test" needs to be marked as
-// testonly = True, forcing other rules that depend on _test rules to also be
-// marked as testonly = True. This semantic constraint is not present in Soong.
-// To work around, rename "*_test" rules to "*_test_".
-func canonicalizeModuleType(moduleName string) string {
-	if strings.HasSuffix(moduleName, "_test") {
-		return moduleName + "_"
-	}
-
-	return moduleName
-}
-
-type RuleShim struct {
-	// The rule class shims contained in a bzl file. e.g. ["cc_object", "cc_library", ..]
-	rules []string
-
-	// The generated string content of the bzl file.
-	content string
-}
-
-// Create <module>.bzl containing Bazel rule shims for every module type available in Soong and
-// user-specified Go plugins.
-//
-// This function reuses documentation generation APIs to ensure parity between modules-as-docs
-// and modules-as-code, including the names and types of module properties.
-func createRuleShims(packages []*bpdoc.Package) (map[string]RuleShim, error) {
-	var propToAttr func(prop bpdoc.Property, propName string) string
-	propToAttr = func(prop bpdoc.Property, propName string) string {
-		// dots are not allowed in Starlark attribute names. Substitute them with double underscores.
-		propName = strings.ReplaceAll(propName, ".", "__")
-		if !shouldGenerateAttribute(propName) {
-			return ""
-		}
-
-		// Canonicalize and normalize module property types to Bazel attribute types
-		starlarkAttrType := prop.Type
-		if starlarkAttrType == "list of string" {
-			starlarkAttrType = "string_list"
-		} else if starlarkAttrType == "int64" {
-			starlarkAttrType = "int"
-		} else if starlarkAttrType == "" {
-			var attr string
-			for _, nestedProp := range prop.Properties {
-				nestedAttr := propToAttr(nestedProp, propName+"__"+nestedProp.Name)
-				if nestedAttr != "" {
-					// TODO(b/167662930): Fix nested props resulting in too many attributes.
-					// Let's still generate these, but comment them out.
-					attr += "# " + nestedAttr
-				}
-			}
-			return attr
-		}
-
-		if !allowedPropTypes[starlarkAttrType] {
-			return ""
-		}
-
-		return fmt.Sprintf("        %q: attr.%s(),\n", propName, starlarkAttrType)
-	}
-
-	ruleShims := map[string]RuleShim{}
-	for _, pkg := range packages {
-		content := "load(\"//build/bazel/queryview_rules:providers.bzl\", \"SoongModuleInfo\")\n"
-
-		bzlFileName := strings.ReplaceAll(pkg.Path, "android/soong/", "")
-		bzlFileName = strings.ReplaceAll(bzlFileName, ".", "_")
-		bzlFileName = strings.ReplaceAll(bzlFileName, "/", "_")
-
-		rules := []string{}
-
-		for _, moduleTypeTemplate := range moduleTypeDocsToTemplates(pkg.ModuleTypes) {
-			attrs := `{
-        "module_name": attr.string(mandatory = True),
-        "module_variant": attr.string(),
-        "module_deps": attr.label_list(providers = [SoongModuleInfo]),
-`
-			for _, prop := range moduleTypeTemplate.Properties {
-				attrs += propToAttr(prop, prop.Name)
-			}
-
-			moduleTypeName := moduleTypeTemplate.Name
-
-			// Certain SDK-related module types dynamically inject properties, instead of declaring
-			// them as structs. These properties are registered in an SdkMemberTypesRegistry. If
-			// the module type name matches, add these properties into the rule definition.
-			var registeredTypes []android.SdkMemberType
-			if moduleTypeName == "module_exports" || moduleTypeName == "module_exports_snapshot" {
-				registeredTypes = android.ModuleExportsMemberTypes.RegisteredTypes()
-			} else if moduleTypeName == "sdk" || moduleTypeName == "sdk_snapshot" {
-				registeredTypes = android.SdkMemberTypes.RegisteredTypes()
-			}
-			for _, memberType := range registeredTypes {
-				attrs += fmt.Sprintf("        %q: attr.string_list(),\n", memberType.SdkPropertyName())
-			}
-
-			attrs += "    },"
-
-			rule := canonicalizeModuleType(moduleTypeTemplate.Name)
-			content += fmt.Sprintf(moduleRuleShim, rule, attrs)
-			rules = append(rules, rule)
-		}
-
-		ruleShims[bzlFileName] = RuleShim{content: content, rules: rules}
-	}
-	return ruleShims, nil
+	})
 }
 
 func createBazelQueryView(ctx *android.Context, bazelQueryViewDir string) error {
-	blueprintCtx := ctx.Context
-	blueprintCtx.VisitAllModules(func(module blueprint.Module) {
-		buildFile, err := buildFileForModule(blueprintCtx, module, bazelQueryViewDir)
-		if err != nil {
-			panic(err)
-		}
-
-		buildFile.Write([]byte(generateSoongModuleTarget(blueprintCtx, module) + "\n\n"))
-		buildFile.Close()
-	})
-	var err error
-
-	// Write top level files: WORKSPACE and BUILD. These files are empty.
-	if err = writeReadOnlyFile(bazelQueryViewDir, "WORKSPACE", ""); err != nil {
-		return err
+	qvCtx := queryviewContext{
+		bpCtx: ctx.Context,
 	}
+	ruleShims := bp2build.CreateRuleShims(android.ModuleTypeFactories())
+	buildToTargets := bp2build.GenerateSoongModuleTargets(&qvCtx)
 
-	// Used to denote that the top level directory is a package.
-	if err = writeReadOnlyFile(bazelQueryViewDir, "BUILD", ""); err != nil {
-		return err
-	}
-
-	packages, err := getPackages(ctx)
-	if err != nil {
-		return err
-	}
-	ruleShims, err := createRuleShims(packages)
-	if err != nil {
-		return err
-	}
-
-	// Write .bzl Starlark files into the bazel_rules top level directory (provider and rule definitions)
-	bazelRulesDir := bazelQueryViewDir + "/build/bazel/queryview_rules"
-	if err = writeReadOnlyFile(bazelRulesDir, "BUILD", ""); err != nil {
-		return err
-	}
-	if err = writeReadOnlyFile(bazelRulesDir, "providers.bzl", providersBzl); err != nil {
-		return err
-	}
-
-	for bzlFileName, ruleShim := range ruleShims {
-		if err = writeReadOnlyFile(bazelRulesDir, bzlFileName+".bzl", ruleShim.content); err != nil {
+	filesToWrite := bp2build.CreateBazelFiles(ruleShims, buildToTargets)
+	for _, f := range filesToWrite {
+		if err := writeReadOnlyFile(bazelQueryViewDir, f); err != nil {
 			return err
 		}
 	}
 
-	return writeReadOnlyFile(bazelRulesDir, "soong_module.bzl", generateSoongModuleBzl(ruleShims))
+	return nil
 }
 
-// Generate the content of soong_module.bzl with the rule shim load statements
-// and mapping of module_type to rule shim map for every module type in Soong.
-func generateSoongModuleBzl(bzlLoads map[string]RuleShim) string {
-	var loadStmts string
-	var moduleRuleMap string
-	for bzlFileName, ruleShim := range bzlLoads {
-		loadStmt := "load(\"//build/bazel/queryview_rules:"
-		loadStmt += bzlFileName
-		loadStmt += ".bzl\""
-		for _, rule := range ruleShim.rules {
-			loadStmt += fmt.Sprintf(", %q", rule)
-			moduleRuleMap += "    \"" + rule + "\": " + rule + ",\n"
-		}
-		loadStmt += ")\n"
-		loadStmts += loadStmt
-	}
-
-	return fmt.Sprintf(soongModuleBzl, loadStmts, moduleRuleMap)
-}
-
-func shouldGenerateAttribute(prop string) bool {
-	return !ignoredPropNames[prop]
-}
-
-// props is an unsorted map. This function ensures that
-// the generated attributes are sorted to ensure determinism.
-func propsToAttributes(props map[string]string) string {
-	var attributes string
-	for _, propName := range android.SortedStringKeys(props) {
-		if shouldGenerateAttribute(propName) {
-			attributes += fmt.Sprintf("    %s = %s,\n", propName, props[propName])
-		}
-	}
-	return attributes
-}
-
-// Convert a module and its deps and props into a Bazel macro/rule
-// representation in the BUILD file.
-func generateSoongModuleTarget(
-	blueprintCtx *blueprint.Context,
-	module blueprint.Module) string {
-
-	var props map[string]string
-	if aModule, ok := module.(android.Module); ok {
-		props = extractModuleProperties(aModule)
-	}
-	attributes := propsToAttributes(props)
-
-	// TODO(b/163018919): DirectDeps can have duplicate (module, variant)
-	// items, if the modules are added using different DependencyTag. Figure
-	// out the implications of that.
-	depLabels := map[string]bool{}
-	blueprintCtx.VisitDirectDeps(module, func(depModule blueprint.Module) {
-		depLabels[qualifiedTargetLabel(blueprintCtx, depModule)] = true
-	})
-
-	depLabelList := "[\n"
-	for depLabel, _ := range depLabels {
-		depLabelList += fmt.Sprintf("        %q,\n", depLabel)
-	}
-	depLabelList += "    ]"
-
-	return fmt.Sprintf(
-		soongModuleTarget,
-		targetNameWithVariant(blueprintCtx, module),
-		blueprintCtx.ModuleName(module),
-		canonicalizeModuleType(blueprintCtx.ModuleType(module)),
-		blueprintCtx.ModuleSubDir(module),
-		depLabelList,
-		attributes)
-}
-
-func buildFileForModule(
-	ctx *blueprint.Context, module blueprint.Module, bazelQueryViewDir string) (*os.File, error) {
-	// Create nested directories for the BUILD file
-	dirPath := filepath.Join(bazelQueryViewDir, packagePath(ctx, module))
-	createDirectoryIfNonexistent(dirPath)
-	// Open the file for appending, and create it if it doesn't exist
-	f, err := os.OpenFile(
-		filepath.Join(dirPath, "BUILD.bazel"),
-		os.O_APPEND|os.O_CREATE|os.O_WRONLY,
-		0644)
-	if err != nil {
-		return nil, err
-	}
-
-	// If the file is empty, add the load statement for the `soong_module` rule
-	fi, err := f.Stat()
-	if err != nil {
-		return nil, err
-	}
-	if fi.Size() == 0 {
-		f.Write([]byte(soongModuleLoad + "\n"))
-	}
-
-	return f, nil
-}
-
-func createDirectoryIfNonexistent(dir string) {
-	if _, err := os.Stat(dir); os.IsNotExist(err) {
-		os.MkdirAll(dir, os.ModePerm)
-	}
-}
-
-// The QueryView directory should be read-only, sufficient for bazel query. The files
+// The auto-conversion directory should be read-only, sufficient for bazel query. The files
 // are not intended to be edited by end users.
-func writeReadOnlyFile(dir string, baseName string, content string) error {
-	createDirectoryIfNonexistent(dir)
-	pathToFile := filepath.Join(dir, baseName)
+func writeReadOnlyFile(dir string, f bp2build.BazelFile) error {
+	dir = filepath.Join(dir, f.Dir)
+	if err := createDirectoryIfNonexistent(dir); err != nil {
+		return err
+	}
+	pathToFile := filepath.Join(dir, f.Basename)
+
 	// 0444 is read-only
-	return ioutil.WriteFile(pathToFile, []byte(content), 0444)
+	err := ioutil.WriteFile(pathToFile, []byte(f.Contents), 0444)
+
+	return err
 }
 
-func isZero(value reflect.Value) bool {
-	switch value.Kind() {
-	case reflect.Func, reflect.Map, reflect.Slice:
-		return value.IsNil()
-	case reflect.Array:
-		valueIsZero := true
-		for i := 0; i < value.Len(); i++ {
-			valueIsZero = valueIsZero && isZero(value.Index(i))
-		}
-		return valueIsZero
-	case reflect.Struct:
-		valueIsZero := true
-		for i := 0; i < value.NumField(); i++ {
-			if value.Field(i).CanSet() {
-				valueIsZero = valueIsZero && isZero(value.Field(i))
-			}
-		}
-		return valueIsZero
-	case reflect.Ptr:
-		if !value.IsNil() {
-			return isZero(reflect.Indirect(value))
-		} else {
-			return true
-		}
-	default:
-		zeroValue := reflect.Zero(value.Type())
-		result := value.Interface() == zeroValue.Interface()
-		return result
+func createDirectoryIfNonexistent(dir string) error {
+	if _, err := os.Stat(dir); os.IsNotExist(err) {
+		return os.MkdirAll(dir, os.ModePerm)
+	} else {
+		return err
 	}
 }
diff --git a/cmd/soong_build/queryview_templates.go b/cmd/soong_build/queryview_templates.go
deleted file mode 100644
index 359c0d8..0000000
--- a/cmd/soong_build/queryview_templates.go
+++ /dev/null
@@ -1,124 +0,0 @@
-// Copyright 2020 Google Inc. All rights reserved.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-package main
-
-const (
-	// The default `load` preamble for every generated BUILD file.
-	soongModuleLoad = `package(default_visibility = ["//visibility:public"])
-load("//build/bazel/queryview_rules:soong_module.bzl", "soong_module")
-
-`
-
-	// A macro call in the BUILD file representing a Soong module, with space
-	// for expanding more attributes.
-	soongModuleTarget = `soong_module(
-    name = "%s",
-    module_name = "%s",
-    module_type = "%s",
-    module_variant = "%s",
-    module_deps = %s,
-%s)`
-
-	// A simple provider to mark and differentiate Soong module rule shims from
-	// regular Bazel rules. Every Soong module rule shim returns a
-	// SoongModuleInfo provider, and can only depend on rules returning
-	// SoongModuleInfo in the `module_deps` attribute.
-	providersBzl = `SoongModuleInfo = provider(
-    fields = {
-        "name": "Name of module",
-        "type": "Type of module",
-        "variant": "Variant of module",
-    },
-)
-`
-
-	// The soong_module rule implementation in a .bzl file.
-	soongModuleBzl = `
-%s
-
-load("//build/bazel/queryview_rules:providers.bzl", "SoongModuleInfo")
-
-def _generic_soong_module_impl(ctx):
-    return [
-        SoongModuleInfo(
-            name = ctx.attr.module_name,
-            type = ctx.attr.module_type,
-            variant = ctx.attr.module_variant,
-        ),
-    ]
-
-generic_soong_module = rule(
-    implementation = _generic_soong_module_impl,
-    attrs = {
-        "module_name": attr.string(mandatory = True),
-        "module_type": attr.string(mandatory = True),
-        "module_variant": attr.string(),
-        "module_deps": attr.label_list(providers = [SoongModuleInfo]),
-    },
-)
-
-soong_module_rule_map = {
-%s}
-
-_SUPPORTED_TYPES = ["bool", "int", "string"]
-
-def _is_supported_type(value):
-    if type(value) in _SUPPORTED_TYPES:
-        return True
-    elif type(value) == "list":
-        supported = True
-        for v in value:
-            supported = supported and type(v) in _SUPPORTED_TYPES
-        return supported
-    else:
-        return False
-
-# soong_module is a macro that supports arbitrary kwargs, and uses module_type to
-# expand to the right underlying shim.
-def soong_module(name, module_type, **kwargs):
-    soong_module_rule = soong_module_rule_map.get(module_type)
-
-    if soong_module_rule == None:
-        # This module type does not have an existing rule to map to, so use the
-        # generic_soong_module rule instead.
-        generic_soong_module(
-            name = name,
-            module_type = module_type,
-            module_name = kwargs.pop("module_name", ""),
-            module_variant = kwargs.pop("module_variant", ""),
-            module_deps = kwargs.pop("module_deps", []),
-        )
-    else:
-        supported_kwargs = dict()
-        for key, value in kwargs.items():
-            if _is_supported_type(value):
-                supported_kwargs[key] = value
-        soong_module_rule(
-            name = name,
-            **supported_kwargs,
-        )
-`
-
-	// A rule shim for representing a Soong module type and its properties.
-	moduleRuleShim = `
-def _%[1]s_impl(ctx):
-    return [SoongModuleInfo()]
-
-%[1]s = rule(
-    implementation = _%[1]s_impl,
-    attrs = %[2]s
-)
-`
-)
diff --git a/cmd/soong_build/queryview_test.go b/cmd/soong_build/queryview_test.go
deleted file mode 100644
index 9471a91..0000000
--- a/cmd/soong_build/queryview_test.go
+++ /dev/null
@@ -1,470 +0,0 @@
-// Copyright 2020 Google Inc. All rights reserved.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-package main
-
-import (
-	"android/soong/android"
-	"io/ioutil"
-	"os"
-	"strings"
-	"testing"
-
-	"github.com/google/blueprint/bootstrap/bpdoc"
-)
-
-var buildDir string
-
-func setUp() {
-	var err error
-	buildDir, err = ioutil.TempDir("", "bazel_queryview_test")
-	if err != nil {
-		panic(err)
-	}
-}
-
-func tearDown() {
-	os.RemoveAll(buildDir)
-}
-
-func TestMain(m *testing.M) {
-	run := func() int {
-		setUp()
-		defer tearDown()
-
-		return m.Run()
-	}
-
-	os.Exit(run())
-}
-
-type customModule struct {
-	android.ModuleBase
-}
-
-// OutputFiles is needed because some instances of this module use dist with a
-// tag property which requires the module implements OutputFileProducer.
-func (m *customModule) OutputFiles(tag string) (android.Paths, error) {
-	return android.PathsForTesting("path" + tag), nil
-}
-
-func (m *customModule) GenerateAndroidBuildActions(ctx android.ModuleContext) {
-	// nothing for now.
-}
-
-func customModuleFactory() android.Module {
-	module := &customModule{}
-	android.InitAndroidModule(module)
-	return module
-}
-
-func TestGenerateBazelQueryViewFromBlueprint(t *testing.T) {
-	testCases := []struct {
-		bp                  string
-		expectedBazelTarget string
-	}{
-		{
-			bp: `custom {
-	name: "foo",
-}
-		`,
-			expectedBazelTarget: `soong_module(
-    name = "foo",
-    module_name = "foo",
-    module_type = "custom",
-    module_variant = "",
-    module_deps = [
-    ],
-)`,
-		},
-		{
-			bp: `custom {
-	name: "foo",
-	ramdisk: true,
-}
-		`,
-			expectedBazelTarget: `soong_module(
-    name = "foo",
-    module_name = "foo",
-    module_type = "custom",
-    module_variant = "",
-    module_deps = [
-    ],
-    ramdisk = True,
-)`,
-		},
-		{
-			bp: `custom {
-	name: "foo",
-	owner: "a_string_with\"quotes\"_and_\\backslashes\\\\",
-}
-		`,
-			expectedBazelTarget: `soong_module(
-    name = "foo",
-    module_name = "foo",
-    module_type = "custom",
-    module_variant = "",
-    module_deps = [
-    ],
-    owner = "a_string_with\"quotes\"_and_\\backslashes\\\\",
-)`,
-		},
-		{
-			bp: `custom {
-	name: "foo",
-	required: ["bar"],
-}
-		`,
-			expectedBazelTarget: `soong_module(
-    name = "foo",
-    module_name = "foo",
-    module_type = "custom",
-    module_variant = "",
-    module_deps = [
-    ],
-    required = [
-        "bar",
-    ],
-)`,
-		},
-		{
-			bp: `custom {
-	name: "foo",
-	target_required: ["qux", "bazqux"],
-}
-		`,
-			expectedBazelTarget: `soong_module(
-    name = "foo",
-    module_name = "foo",
-    module_type = "custom",
-    module_variant = "",
-    module_deps = [
-    ],
-    target_required = [
-        "qux",
-        "bazqux",
-    ],
-)`,
-		},
-		{
-			bp: `custom {
-	name: "foo",
-	dist: {
-		targets: ["goal_foo"],
-		tag: ".foo",
-	},
-	dists: [
-		{
-			targets: ["goal_bar"],
-			tag: ".bar",
-		},
-	],
-}
-		`,
-			expectedBazelTarget: `soong_module(
-    name = "foo",
-    module_name = "foo",
-    module_type = "custom",
-    module_variant = "",
-    module_deps = [
-    ],
-    dist = {
-        "tag": ".foo",
-        "targets": [
-            "goal_foo",
-        ],
-    },
-    dists = [
-        {
-            "tag": ".bar",
-            "targets": [
-                "goal_bar",
-            ],
-        },
-    ],
-)`,
-		},
-		{
-			bp: `custom {
-	name: "foo",
-	required: ["bar"],
-	target_required: ["qux", "bazqux"],
-	ramdisk: true,
-	owner: "custom_owner",
-	dists: [
-		{
-			tag: ".tag",
-			targets: ["my_goal"],
-		},
-	],
-}
-		`,
-			expectedBazelTarget: `soong_module(
-    name = "foo",
-    module_name = "foo",
-    module_type = "custom",
-    module_variant = "",
-    module_deps = [
-    ],
-    dists = [
-        {
-            "tag": ".tag",
-            "targets": [
-                "my_goal",
-            ],
-        },
-    ],
-    owner = "custom_owner",
-    ramdisk = True,
-    required = [
-        "bar",
-    ],
-    target_required = [
-        "qux",
-        "bazqux",
-    ],
-)`,
-		},
-	}
-
-	for _, testCase := range testCases {
-		config := android.TestConfig(buildDir, nil, testCase.bp, nil)
-		ctx := android.NewTestContext(config)
-		ctx.RegisterModuleType("custom", customModuleFactory)
-		ctx.Register()
-
-		_, errs := ctx.ParseFileList(".", []string{"Android.bp"})
-		android.FailIfErrored(t, errs)
-		_, errs = ctx.PrepareBuildActions(config)
-		android.FailIfErrored(t, errs)
-
-		module := ctx.ModuleForTests("foo", "").Module().(*customModule)
-		blueprintCtx := ctx.Context.Context
-
-		actualBazelTarget := generateSoongModuleTarget(blueprintCtx, module)
-		if actualBazelTarget != testCase.expectedBazelTarget {
-			t.Errorf(
-				"Expected generated Bazel target to be '%s', got '%s'",
-				testCase.expectedBazelTarget,
-				actualBazelTarget,
-			)
-		}
-	}
-}
-
-func createPackageFixtures() []*bpdoc.Package {
-	properties := []bpdoc.Property{
-		bpdoc.Property{
-			Name: "int64_prop",
-			Type: "int64",
-		},
-		bpdoc.Property{
-			Name: "int_prop",
-			Type: "int",
-		},
-		bpdoc.Property{
-			Name: "bool_prop",
-			Type: "bool",
-		},
-		bpdoc.Property{
-			Name: "string_prop",
-			Type: "string",
-		},
-		bpdoc.Property{
-			Name: "string_list_prop",
-			Type: "list of string",
-		},
-		bpdoc.Property{
-			Name: "nested_prop",
-			Type: "",
-			Properties: []bpdoc.Property{
-				bpdoc.Property{
-					Name: "int_prop",
-					Type: "int",
-				},
-				bpdoc.Property{
-					Name: "bool_prop",
-					Type: "bool",
-				},
-				bpdoc.Property{
-					Name: "string_prop",
-					Type: "string",
-				},
-			},
-		},
-		bpdoc.Property{
-			Name: "unknown_type",
-			Type: "unknown",
-		},
-	}
-
-	fooPropertyStruct := &bpdoc.PropertyStruct{
-		Name:       "FooProperties",
-		Properties: properties,
-	}
-
-	moduleTypes := []*bpdoc.ModuleType{
-		&bpdoc.ModuleType{
-			Name: "foo_library",
-			PropertyStructs: []*bpdoc.PropertyStruct{
-				fooPropertyStruct,
-			},
-		},
-
-		&bpdoc.ModuleType{
-			Name: "foo_binary",
-			PropertyStructs: []*bpdoc.PropertyStruct{
-				fooPropertyStruct,
-			},
-		},
-		&bpdoc.ModuleType{
-			Name: "foo_test",
-			PropertyStructs: []*bpdoc.PropertyStruct{
-				fooPropertyStruct,
-			},
-		},
-	}
-
-	return [](*bpdoc.Package){
-		&bpdoc.Package{
-			Name:        "foo_language",
-			Path:        "android/soong/foo",
-			ModuleTypes: moduleTypes,
-		},
-	}
-}
-
-func TestGenerateModuleRuleShims(t *testing.T) {
-	ruleShims, err := createRuleShims(createPackageFixtures())
-	if err != nil {
-		panic(err)
-	}
-
-	if len(ruleShims) != 1 {
-		t.Errorf("Expected to generate 1 rule shim, but got %d", len(ruleShims))
-	}
-
-	fooRuleShim := ruleShims["foo"]
-	expectedRules := []string{"foo_binary", "foo_library", "foo_test_"}
-
-	if len(fooRuleShim.rules) != 3 {
-		t.Errorf("Expected 3 rules, but got %d", len(fooRuleShim.rules))
-	}
-
-	for i, rule := range fooRuleShim.rules {
-		if rule != expectedRules[i] {
-			t.Errorf("Expected rule shim to contain %s, but got %s", expectedRules[i], rule)
-		}
-	}
-
-	expectedBzl := `load("//build/bazel/queryview_rules:providers.bzl", "SoongModuleInfo")
-
-def _foo_binary_impl(ctx):
-    return [SoongModuleInfo()]
-
-foo_binary = rule(
-    implementation = _foo_binary_impl,
-    attrs = {
-        "module_name": attr.string(mandatory = True),
-        "module_variant": attr.string(),
-        "module_deps": attr.label_list(providers = [SoongModuleInfo]),
-        "bool_prop": attr.bool(),
-        "int64_prop": attr.int(),
-        "int_prop": attr.int(),
-#         "nested_prop__int_prop": attr.int(),
-#         "nested_prop__bool_prop": attr.bool(),
-#         "nested_prop__string_prop": attr.string(),
-        "string_list_prop": attr.string_list(),
-        "string_prop": attr.string(),
-    },
-)
-
-def _foo_library_impl(ctx):
-    return [SoongModuleInfo()]
-
-foo_library = rule(
-    implementation = _foo_library_impl,
-    attrs = {
-        "module_name": attr.string(mandatory = True),
-        "module_variant": attr.string(),
-        "module_deps": attr.label_list(providers = [SoongModuleInfo]),
-        "bool_prop": attr.bool(),
-        "int64_prop": attr.int(),
-        "int_prop": attr.int(),
-#         "nested_prop__int_prop": attr.int(),
-#         "nested_prop__bool_prop": attr.bool(),
-#         "nested_prop__string_prop": attr.string(),
-        "string_list_prop": attr.string_list(),
-        "string_prop": attr.string(),
-    },
-)
-
-def _foo_test__impl(ctx):
-    return [SoongModuleInfo()]
-
-foo_test_ = rule(
-    implementation = _foo_test__impl,
-    attrs = {
-        "module_name": attr.string(mandatory = True),
-        "module_variant": attr.string(),
-        "module_deps": attr.label_list(providers = [SoongModuleInfo]),
-        "bool_prop": attr.bool(),
-        "int64_prop": attr.int(),
-        "int_prop": attr.int(),
-#         "nested_prop__int_prop": attr.int(),
-#         "nested_prop__bool_prop": attr.bool(),
-#         "nested_prop__string_prop": attr.string(),
-        "string_list_prop": attr.string_list(),
-        "string_prop": attr.string(),
-    },
-)
-`
-
-	if fooRuleShim.content != expectedBzl {
-		t.Errorf(
-			"Expected the generated rule shim bzl to be:\n%s\nbut got:\n%s",
-			expectedBzl,
-			fooRuleShim.content)
-	}
-}
-
-func TestGenerateSoongModuleBzl(t *testing.T) {
-	ruleShims, err := createRuleShims(createPackageFixtures())
-	if err != nil {
-		panic(err)
-	}
-	actualSoongModuleBzl := generateSoongModuleBzl(ruleShims)
-
-	expectedLoad := "load(\"//build/bazel/queryview_rules:foo.bzl\", \"foo_binary\", \"foo_library\", \"foo_test_\")"
-	expectedRuleMap := `soong_module_rule_map = {
-    "foo_binary": foo_binary,
-    "foo_library": foo_library,
-    "foo_test_": foo_test_,
-}`
-	if !strings.Contains(actualSoongModuleBzl, expectedLoad) {
-		t.Errorf(
-			"Generated soong_module.bzl:\n\n%s\n\n"+
-				"Could not find the load statement in the generated soong_module.bzl:\n%s",
-			actualSoongModuleBzl,
-			expectedLoad)
-	}
-
-	if !strings.Contains(actualSoongModuleBzl, expectedRuleMap) {
-		t.Errorf(
-			"Generated soong_module.bzl:\n\n%s\n\n"+
-				"Could not find the module -> rule map in the generated soong_module.bzl:\n%s",
-			actualSoongModuleBzl,
-			expectedRuleMap)
-	}
-}
