Skip to content

Commit 369a5fa

Browse files
devversionclydin
authored andcommitted
build: create ts_project interop allowing for incremental migration
This commit introduces a new interop Starlark macro/rule for using `ts_project` throughout the repository without having to migrate any dependant or dependencies; allowing for incremental migration to `ts_project`.
1 parent afc75ce commit 369a5fa

File tree

3 files changed

+116
-1
lines changed

3 files changed

+116
-1
lines changed

BUILD.bazel

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,15 @@ rules_js_tsconfig(
3535
],
3636
)
3737

38+
rules_js_tsconfig(
39+
name = "test-tsconfig",
40+
src = "tsconfig-test.json",
41+
deps = [
42+
"tsconfig.json",
43+
"//:node_modules/@types/node",
44+
],
45+
)
46+
3847
# Files required by e2e tests
3948
copy_to_bin(
4049
name = "config-files",

tools/interop.bzl

Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
load("@aspect_rules_js//js:providers.bzl", "JsInfo", "js_info")
2+
load("@aspect_rules_ts//ts:defs.bzl", _ts_project = "ts_project")
3+
load("@rules_nodejs//nodejs:providers.bzl", "DeclarationInfo", "JSModuleInfo", "LinkablePackageInfo")
4+
5+
def _ts_deps_interop_impl(ctx):
6+
types = []
7+
sources = []
8+
runfiles = ctx.runfiles(files = [])
9+
for dep in ctx.attr.deps:
10+
if not DeclarationInfo in dep:
11+
fail("Expected target with DeclarationInfo: %s", dep)
12+
types.append(dep[DeclarationInfo].transitive_declarations)
13+
if not JSModuleInfo in dep:
14+
fail("Expected target with JSModuleInfo: %s", dep)
15+
sources.append(dep[JSModuleInfo].sources)
16+
if not DefaultInfo in dep:
17+
fail("Expected target with DefaultInfo: %s", dep)
18+
runfiles = runfiles.merge(dep[DefaultInfo].default_runfiles)
19+
20+
return [
21+
DefaultInfo(runfiles = runfiles),
22+
## NOTE: We don't need to propagate module mappings FORTUNATELY!
23+
# because rules_nodejs supports tsconfig path mapping, given that
24+
# everything is nicely compiled from `bazel-bin/`!
25+
js_info(
26+
target = ctx.label,
27+
transitive_types = depset(transitive = types),
28+
transitive_sources = depset(transitive = sources),
29+
),
30+
]
31+
32+
ts_deps_interop = rule(
33+
implementation = _ts_deps_interop_impl,
34+
attrs = {
35+
"deps": attr.label_list(providers = [DeclarationInfo], mandatory = True),
36+
},
37+
)
38+
39+
def _ts_project_module_impl(ctx):
40+
# Forward runfiles. e.g. JSON files on `ts_project#data`. The jasmine
41+
# consuming rules may rely on this, or the linker due to its symlinks then.
42+
runfiles = ctx.attr.dep[DefaultInfo].default_runfiles
43+
info = ctx.attr.dep[JsInfo]
44+
45+
providers = [
46+
DefaultInfo(
47+
runfiles = runfiles,
48+
),
49+
JSModuleInfo(
50+
direct_sources = info.sources,
51+
sources = depset(transitive = [info.transitive_sources]),
52+
),
53+
DeclarationInfo(
54+
declarations = info.types,
55+
transitive_declarations = info.transitive_types,
56+
type_blocklisted_declarations = depset(),
57+
),
58+
]
59+
60+
if ctx.attr.module_name:
61+
providers.append(
62+
LinkablePackageInfo(
63+
package_name = ctx.attr.module_name,
64+
package_path = "",
65+
path = "%s/%s/%s" % (ctx.bin_dir.path, ctx.label.workspace_root, ctx.label.package),
66+
files = info.sources,
67+
),
68+
)
69+
70+
return providers
71+
72+
ts_project_module = rule(
73+
implementation = _ts_project_module_impl,
74+
attrs = {
75+
"dep": attr.label(providers = [JsInfo], mandatory = True),
76+
# Noop attribute for aspect propagation of the linker interop deps; so
77+
# that transitive linker dependencies are discovered.
78+
"deps": attr.label_list(),
79+
# Note: The module aspect from consuming `ts_library` targets will
80+
# consume the module mappings automatically.
81+
"module_name": attr.string(),
82+
},
83+
)
84+
85+
def ts_project(name, module_name = None, interop_deps = [], deps = [], testonly = False, **kwargs):
86+
ts_deps_interop(
87+
name = "%s_interop_deps" % name,
88+
deps = interop_deps,
89+
testonly = testonly,
90+
)
91+
92+
_ts_project(
93+
name = "%s_rjs" % name,
94+
testonly = testonly,
95+
tsconfig = "//:test-tsconfig" if testonly else "//:build-tsconfig",
96+
declaration = True,
97+
deps = ["%s_interop_deps" % name] + deps,
98+
**kwargs
99+
)
100+
101+
ts_project_module(
102+
name = name,
103+
testonly = testonly,
104+
dep = "%s_rjs" % name,
105+
deps = interop_deps,
106+
module_name = module_name,
107+
)

tsconfig.json

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@
99
"noFallthroughCasesInSwitch": true,
1010
"noImplicitOverride": true,
1111
"isolatedModules": true,
12-
"outDir": "./dist",
1312
"skipLibCheck": true,
1413
"strict": true,
1514
"target": "es2022",

0 commit comments

Comments
 (0)