Skip to content

Instantly share code, notes, and snippets.

@Esfera5
Created July 14, 2018 20:46
Show Gist options
  • Save Esfera5/16e082595eb29f202cbdeb6236bb0657 to your computer and use it in GitHub Desktop.
Save Esfera5/16e082595eb29f202cbdeb6236bb0657 to your computer and use it in GitHub Desktop.
EclipseProjectInfo = provider(
fields=["project_name", "package_name", "folders", "projects", "jars"]
)
def _generate_eclipse_project_file(ctx, info):
project_lines = [
'<?xml version="1.0" encoding="UTF-8"?>',
'<!-- DO NOT EDIT - AUTOMATICALLY GENERATED -->',
'<projectDescription>',
' <name>%s</name>' % info.project_name,
' <comment></comment>',
' <projects></projects>',
' <buildSpec>',
' <buildCommand>',
' <name>org.eclipse.jdt.core.javabuilder</name>',
' <arguments></arguments>',
' </buildCommand>',
' </buildSpec>',
' <natures>',
' <nature>org.eclipse.jdt.core.javanature</nature>',
' </natures>',
'</projectDescription>',
'',
]
ctx.actions.write(
output = ctx.outputs.project,
content = "\n".join(project_lines))
def _render_classpath_entry(kind, path, comment='', attrs={}):
if comment:
comment = '<!-- %s -->\n ' % comment
extra = ' '.join(['%s="%s"' % kv for kv in attrs.items()])
return ' %s<classpathentry kind="%s" path="%s" %s/>' % (comment, kind, path, extra)
def _generate_eclipse_classpath_file(ctx, info):
entries = [
_render_classpath_entry('output', 'bin'),
_render_classpath_entry('con', 'org.eclipse.jdt.launching.JRE_CONTAINER'),
]
for folder in info.folders:
entries.append(_render_classpath_entry('src', folder))
for project in info.projects:
entries.append(_render_classpath_entry('src', '/' + project[1],
comment='project=%s' % project[0],
attrs={'combineaccessrules': 'false'}))
for jar in info.jars:
entries.append(_render_classpath_entry('src', jar[1], comment='jar=%s' % jar[0]))
classpath_lines = [
'<?xml version="1.0" encoding="UTF-8"?>',
'<!-- DO NOT EDIT - AUTOMATICALLY GENERATED -->',
'<classpath>',
'\n'.join(entries),
'</classpath>',
'',
]
ctx.actions.write(
output = ctx.outputs.classpath,
content = "\n".join(classpath_lines))
def _list_output_jars(dep):
jars = []
for jar in dep.java.outputs.jars:
jars.append((str(dep.label), jar.class_jar.path))
if not jars:
for file in dep.files:
if not file.path.endswith("-src.jar"):
jars.append((str(dep.label), file.path))
return jars
def _eclipse_project_impl(ctx):
seen_package_names = {}
seen_package_names[ctx.label.package] = True
projects = []
for dep in ctx.attr.deps:
if EclipseProjectInfo in dep:
info = dep[EclipseProjectInfo]
projects.append((str(dep.label), info.project_name))
seen_package_names[info.package_name] = True
seen_jars = {}
jars = []
for dep in ctx.attr.deps:
if hasattr(dep, 'java'):
if dep.label.workspace_root == '' and dep.label.package in seen_package_names:
print(dep.label)
continue
for jar in _list_output_jars(dep):
if jar not in seen_jars:
seen_jars[jar] = True
jars.append(jar)
info = EclipseProjectInfo(
project_name = ctx.attr.project_name,
package_name = ctx.attr.package_name,
folders = ctx.attr.folders,
projects = projects,
jars = jars,
)
_generate_eclipse_project_file(ctx, info)
_generate_eclipse_classpath_file(ctx, info)
return [info]
_eclipse_project = rule(
implementation = _eclipse_project_impl,
attrs = {
'project_name': attr.string(mandatory=True),
'package_name': attr.string(),
'folders': attr.string_list(),
'deps': attr.label_list(),
},
outputs = {
"classpath": ".classpath",
"project": ".project",
},
)
def eclipse_project(name, project_name, folders=[], deps=[]):
local_deps = []
for r in native.existing_rules().values():
r_deps = r.get('deps', [])
if r_deps and r.get('kind', '').startswith('java_'):
local_deps.extend(r_deps)
if not folders:
folders = ["src", "test"]
_eclipse_project(
name = name,
project_name = project_name,
package_name = native.package_name(),
folders = folders,
deps = local_deps + deps,
)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment