fbcode_builder: add cargo builder for Rust projects

Summary: The cargo builder will be used to verify if an opensource Rust project passes Cargo build, test and (optionally) documentation build.

Reviewed By: markbt

Differential Revision: D18636934

fbshipit-source-id: e982e6a017eb32913e2994e7457c8add2e9d6b95
This commit is contained in:
Lukas Piatkowski 2019-11-28 04:57:12 -08:00 committed by Facebook Github Bot
parent 526fbc8ec2
commit a8ebf55e26
3 changed files with 88 additions and 1 deletions

View File

@ -5,7 +5,6 @@
from __future__ import absolute_import, division, print_function, unicode_literals
import glob
import json
import os
import shutil
@ -789,3 +788,62 @@ install(FILES sqlite3.h sqlite3ext.h DESTINATION include)
],
env=env,
)
class CargoBuilder(BuilderBase):
def __init__(
self, build_opts, ctx, manifest, src_dir, build_dir, inst_dir, build_doc
):
super(CargoBuilder, self).__init__(
build_opts, ctx, manifest, src_dir, build_dir, inst_dir
)
self.build_doc = build_doc
def run_cargo(self, install_dirs, operation, args=None):
args = args or []
env = self._compute_env(install_dirs)
cmd = ["cargo", operation, "-j%s" % self.build_opts.num_jobs] + args
self._run_cmd(cmd, cwd=self.build_source_dir(), env=env)
def build_source_dir(self):
return os.path.join(self.build_dir, "source")
def recreate_dir(self, src, dst):
if os.path.isdir(dst):
shutil.rmtree(dst)
shutil.copytree(src, dst)
def _build(self, install_dirs, reconfigure):
build_source_dir = self.build_source_dir()
self.recreate_dir(self.src_dir, build_source_dir)
dot_cargo_dir = os.path.join(build_source_dir, ".cargo")
if not os.path.isdir(dot_cargo_dir):
os.mkdir(dot_cargo_dir)
with open(os.path.join(dot_cargo_dir, "config"), "w+") as f:
f.write(
"""\
[build]
target-dir = '''{}'''
""".format(
self.build_dir.replace("\\", "\\\\")
)
)
try:
from getdeps.facebook.lfs import crates_io_download
crates_io_download(self.build_opts, self.build_dir, build_source_dir)
except ImportError:
# This FB internal module isn't shippped to github,
# so just rely on cargo downloading crates on it's own
pass
self.run_cargo(install_dirs, "build")
self.recreate_dir(build_source_dir, os.path.join(self.inst_dir, "source"))
def run_tests(self, install_dirs, schedule_type, owner):
self.run_cargo(install_dirs, "test")
if self.build_doc:
self.run_cargo(install_dirs, "doc", ["--no-deps"])

View File

@ -12,6 +12,7 @@ import os
from .builder import (
AutoconfBuilder,
Boost,
CargoBuilder,
CMakeBuilder,
Iproute2Builder,
MakeBuilder,
@ -67,6 +68,7 @@ SCHEMA = {
},
},
"msbuild": {"optional_section": True, "fields": {"project": REQUIRED}},
"cargo": {"optional_section": True, "fields": {"build_doc": OPTIONAL}},
"cmake.defines": {"optional_section": True},
"autoconf.args": {"optional_section": True},
"b2.args": {"optional_section": True},
@ -416,6 +418,12 @@ class ManifestParser(object):
build_options, ctx, self, src_dir, build_dir, inst_dir
)
if builder == "cargo":
build_doc = self.get("cargo", "build_doc", False, ctx)
return CargoBuilder(
build_options, ctx, self, src_dir, build_dir, inst_dir, build_doc
)
raise KeyError("project %s has no known builder" % (self.name))

View File

@ -0,0 +1,21 @@
[manifest]
name = rust-shed
fbsource_path = fbcode/common/rust/shed
shipit_project = rust-shed
shipit_fbcode_builder = true
[git]
repo_url = https://github.com/facebookexperimental/rust-shed.git
[build]
builder = cargo
[cargo]
build_doc = true
[shipit.pathmap]
fbcode/common/rust/shed = .
fbcode/common/rust/shed/public_tld = .
[dependencies]
fbthrift