forked from fwouts/bazel-javascript
-
Notifications
You must be signed in to change notification settings - Fork 0
/
context.bzl
150 lines (121 loc) · 4.55 KB
/
context.bzl
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
load("//internal/common/actions:actions.bzl", "create_compilation_dir", "run_js")
load("//internal/npm_packages:rule.bzl", "NpmPackagesInfo")
###############################################################################
# Providers
# Wrapper for rule ctx that should be created through js_context
JsContext = provider()
# Javascript compilation sources
JsSource = provider(fields = [
# Path of the BUILD.bazel file relative to the workspace root.
"build_file_path",
# Source files provided as input.
"sources",
# All source files
"all_sources",
# Depset of npm_packages
"npm_packages",
])
# Javascript files that can be included as a built dependency
JsLibrary = provider(fields = [
# JsSource object for the source used to build the library
"source",
# Directory with the compiled sources (like pkg.lib)
"library_dir",
])
JsPackage = provider(
fields = [
# JsLibrary object for the
"library",
# Name that will be used for non relative imports
"package_name",
],
)
###############################################################################
# Helpers
def _js_source(js, attr):
"""Create a JsSource provider with attr.srcs and the sources from attr.deps
Args:
js: JsContext object
attr: rule attributes to extract srcs and deps from
"""
# The srcs should contain what has been explicitly added for a rule
srcs_attr = getattr(attr, "srcs", [])
# The deps is list of labels that should have providers that we can get sources from
deps_attr = getattr(attr, "deps", [])
all_transitive_sources = [dep[JsSource].all_sources for dep in deps_attr if JsSource in dep]
all_sources = depset(
direct = srcs_attr,
transitive = all_transitive_sources,
)
direct_npm_packages = [dep[NpmPackagesInfo] for dep in ctx.attr.deps if NpmPackagesInfo in dep]
if len(direct_npm_packages) > 1:
fail("Found more than one set of NPM packages in target definition: " + ",".join([
dep.label
for dep in direct_npm_packages
]))
extended_npm_packages = depset(
direct = direct_npm_packages,
transitive = [
dep[JsLibraryInfo].npm_packages
for dep in ctx.attr.deps
if JsLibraryInfo in dep
],
)
npm_packages_list = extended_npm_packages.to_list()
if len(npm_packages_list) > 1:
fail("Found more than one set of NPM packages through dependencies: " + ",".join([
dep.label
for dep in npm_packages_list
]))
return JsSource(
build_file_path = js.build_file_path,
sources = srcs_attr,
all_sources = internal_deps,
npm_packages = extended_npm_packages,
)
def _js_library(js, name, source):
"""Create a JsLibrary provider
Args:
js: JsContext object
"""
def _script_args(js, script_file):
"""Create Args object that can be used with js.run_js()
Args:
js: JsContext object
script_file: File object for the script to be run
"""
if not script_file is File:
fail("script_file not supplied to script_args")
args = js.actions.args()
# Add the script to run
args.add(script_file)
# If the args get too big then spill over into the param file
args.use_param_file("--param=%s")
args.set_param_file_format("multiline")
# Following pattern similar to rules_go
# https:/bazelbuild/rules_go/blob/2179a6e1b576fc2a309c6cf677ad40e5b7f999ba/go/private/context.bzl#L207
def js_context(ctx, attr = None):
if not attr:
attr = ctx.attr
# Node js to be used to run javascript backed bazel actions
_internal_nodejs = getattr(attr, "_internal_nodejs", Label("@nodejs//:node"))
# Packages that will be made available to javascript backed bazel actions
_internal_packages = getattr(attr, "_internal_packages", Label("//internal/packages"))
# Packages that will be used if none are provided
_empty_npm_packages = getattr(attr, "_empty_npm_packages", Label("//internal/npm_packages/empty:packages"))
return JsContext(
# Fields
workspace_name = ctx.workspace_name,
build_file_path = ctx.build_file_path,
_ctx = ctx,
_internal_nodejs = _internal_nodejs,
_internal_packages = _internal_packages,
_empty_npm_packages = _empty_npm_packages,
#Actions
actions = ctx.actions,
create_compilation_dir = create_compilation_dir,
run_js = run_js,
#Helpers
script_args = _script_args,
js_source = _js_source,
)