CMake: Make it easier for projects to consume sandboxed libraries

This change starts with Jsonnet as the canonical, ready-made sandboxed library
example. Follow-up changes should similarly migrate the OSS Internship
sandboxes.

- Add an `add_sapi_subdirectory()` which sets up source and binary directories
  correctly when consuming SAPI as sub-project
- Restructure the Jsonnet `CMakeLists.txt` and simplify header inclusions
- Update the Jsonnet README file

PiperOrigin-RevId: 425818479
Change-Id: Iba9e83201863b4ad8a91914397b310d9d4230423
This commit is contained in:
Christian Blichmann 2022-02-02 01:09:26 -08:00 committed by Copybara-Service
parent 2a8fca56fd
commit ee5ebaa48f
15 changed files with 102 additions and 72 deletions

View File

@ -189,3 +189,14 @@ function(sapi_protobuf_generate)
target_sources(${_pb_TARGET} PRIVATE ${_generated_srcs_all})
endif()
endfunction()
# Adds a sub-directory from Sandboxed API to the build. This is a simple macro
# that calls `add_subdirectory()` with Sandboxed API's source and binary
# directories and `EXCLUDE_FROM_ALL`.
# This is useful in embedding projects to be able to refer to pre-sandboxed
# libraries easily.
macro(add_sapi_subdirectory)
add_subdirectory("${SAPI_SOURCE_DIR}/${ARGV0}"
"${SAPI_BINARY_DIR}/${ARGV0}"
EXCLUDE_FROM_ALL)
endmacro()

View File

@ -3,6 +3,12 @@
This directory contains reusable Sandboxed API integrations with external
libraries.
## Projects Sandboxed
Directory | Project | Home Page | Integration
---------- | -------------------------------------- | -------------------------------------------------------------- | -----------
`jsonnet/` | Jsonnet - The Data Templating Language | [github.com/google/jsonnet](https://github.com/google/jsonnet) | CMake
## Projects Shipping with Sandboxed API Sandboxes
Project | Home Page | Integration

View File

@ -18,11 +18,12 @@ project(jsonnet-sapi C CXX)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED True)
set(SAPI_ROOT "../.." CACHE PATH "Path to the Sandboxed API source tree")
add_subdirectory("${SAPI_ROOT}"
"${CMAKE_BINARY_DIR}/sandboxed-api-build"
EXCLUDE_FROM_ALL)
if(NOT TARGET sapi::sapi)
set(SAPI_ROOT "../.." CACHE PATH "Path to the Sandboxed API source tree")
add_subdirectory("${SAPI_ROOT}"
"${CMAKE_BINARY_DIR}/sandboxed-api-build"
EXCLUDE_FROM_ALL)
endif()
FetchContent_Declare(jsonnet
GIT_REPOSITORY https://github.com/google/jsonnet.git
@ -33,7 +34,32 @@ FetchContent_MakeAvailable(jsonnet)
create_directory_symlink("${jsonnet_SOURCE_DIR}"
"${PROJECT_BINARY_DIR}/jsonnet")
add_subdirectory(examples)
configure_file("${jsonnet_SOURCE_DIR}/cmd/jsonnet.cpp"
"${PROJECT_BINARY_DIR}/gen_files/jsonnet.cpp" COPYONLY)
add_custom_command(
OUTPUT "${PROJECT_BINARY_DIR}/gen_files/write_helper.cc"
WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/gen_files"
COMMAND patch -o write_helper.cc
< "${PROJECT_SOURCE_DIR}/jsonnet.patch" > /dev/null
)
add_library(jsonnet_helper STATIC
"${PROJECT_BINARY_DIR}/gen_files/write_helper.cc"
"${jsonnet_SOURCE_DIR}/cmd/utils.cpp"
"${jsonnet_SOURCE_DIR}/cmd/utils.h"
jsonnet_helper.cc
jsonnet_helper.h
)
add_library(sapi_contrib::jsonnet_helper ALIAS jsonnet_helper)
target_include_directories(jsonnet_helper PUBLIC
"${PROJECT_BINARY_DIR}"
"${PROJECT_BINARY_DIR}/gen_files"
"${SAPI_SOURCE_DIR}"
)
target_link_libraries(jsonnet_helper
libjsonnet_for_binaries
)
add_sapi_library(jsonnet_sapi
FUNCTIONS c_free_input
@ -53,12 +79,17 @@ add_sapi_library(jsonnet_sapi
LIBRARY_NAME Jsonnet
NAMESPACE ""
)
add_library(sapi_contrib::jsonnet ALIAS jsonnet_sapi)
target_include_directories(jsonnet_sapi INTERFACE
"${PROJECT_BINARY_DIR}"
)
target_link_libraries(jsonnet_sapi PUBLIC
sapi_contrib::jsonnet_helper
)
target_link_libraries(jsonnet_sapi PUBLIC jsonnet_helper)
if(SAPI_ENABLE_EXAMPLES)
add_subdirectory(examples)
endif()
if(SAPI_ENABLE_TESTS)
include(GoogleTest)
@ -80,10 +111,10 @@ if(SAPI_ENABLE_TESTS)
jsonnet_tests.cc
)
target_include_directories(jsonnet_tests PUBLIC
${PROJECT_SOURCE_DIR}
"${PROJECT_SOURCE_DIR}"
)
target_link_libraries(jsonnet_tests
jsonnet_sapi
sapi_contrib::jsonnet
sapi::test_main
)
gtest_discover_tests(jsonnet_tests)

View File

@ -3,6 +3,29 @@
This library provides a sandboxed version of the
[Jsonnet](https://github.com/google/jsonnet) library.
## How to use from an existing Project
If your project does not include Sandboxed API as a dependency yet, add the
following lines to the main `CMakeLists.txt`:
```cmake
include(FetchContent)
FetchContent_Declare(sandboxed-api
GIT_REPOSITORY https://github.com/google/sandboxed-api
GIT_TAG main # Or pin a specific commit/tag
)
FetchContent_MakeAvailable(sandboxed-api) # CMake 3.14 or higher
add_sapi_subdirectory(contrib/jsonnet)
```
The `add_sapi_subdirectory()` macro sets up the source and binary directories
for the sandboxed jsonnet targets.
Afterwards your project's code can link to `sapi_contrib::jsonnet` and use the
corresponding header `contrib/jsonnet/jsonnet_base_sandbox.h`.
## Examples
The `examples/` directory contains code to produce three command-line tools --
@ -20,10 +43,10 @@ executable. It is based on a tool found from
a jsonnet code formatter -- it changes poorly written jsonnet files into their
canonical form.
## Build
### Build as part of Sandboxed API
To build these examples, after cloning the whole Sandbox API project, this
in the `sandboxed-api/oss-internship-2020/jsonnet`:
To build these examples, after cloning the whole Sandbox API project, run this
in the `contrib/jsonnet` directory:
```
mkdir -p build && cd build
@ -66,7 +89,7 @@ The formatter reads one input file and produces one output file as a result.
Example code for this tool can also be found in `examples/jsonnet_codes`
directory, in a file called `formatter_example.jsonnet`.
## Testing
### Running the tests
A few tests prepared with a use of
[Google Test](https://github.com/google/googletest) framework are included. To

View File

@ -12,55 +12,18 @@
# See the License for the specific language governing permissions and
# limitations under the License.
configure_file("${jsonnet_SOURCE_DIR}/cmd/jsonnet.cpp"
"${PROJECT_BINARY_DIR}/gen_files/jsonnet.cpp" COPYONLY)
add_custom_command(
OUTPUT "${PROJECT_BINARY_DIR}/gen_files/write_helper.cc"
WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/gen_files"
COMMAND patch -o write_helper.cc
< "${PROJECT_SOURCE_DIR}/jsonnet.patch" > /dev/null
)
list(APPEND JSONNET_SAPI_INCLUDE_DIRS
${PROJECT_SOURCE_DIR}
${PROJECT_BINARY_DIR}
${PROJECT_BINARY_DIR}/gen_files
)
add_library(jsonnet_helper STATIC
${PROJECT_SOURCE_DIR}/jsonnet_helper.cc
${PROJECT_SOURCE_DIR}/jsonnet_helper.h
${jsonnet_SOURCE_DIR}/cmd/utils.h
${jsonnet_SOURCE_DIR}/cmd/utils.cpp
${PROJECT_BINARY_DIR}/gen_files/write_helper.cc
)
target_include_directories(jsonnet_helper PUBLIC
${JSONNET_SAPI_INCLUDE_DIRS}
)
target_link_libraries(jsonnet_helper
libjsonnet_for_binaries
)
foreach(target IN ITEMS base multiple_files yaml_stream formatter)
add_executable(jsonnet_${target}_sandboxed
jsonnet_${target}_example.cc
)
target_link_libraries(jsonnet_${target}_sandboxed PRIVATE
libjsonnet
jsonnet_helper
jsonnet_sapi
sapi_contrib::jsonnet_helper
sapi_contrib::jsonnet
sapi::file_base
sapi::fileops
sapi::sapi
)
target_include_directories(jsonnet_${target}_sandboxed PUBLIC
${JSONNET_SAPI_INCLUDE_DIRS}
)
endforeach()
add_executable(jsonnet_base_transacted
@ -69,7 +32,7 @@ add_executable(jsonnet_base_transacted
target_link_libraries(jsonnet_base_transacted PRIVATE
libjsonnet
jsonnet_helper
jsonnet_sapi
sapi_contrib::jsonnet_helper
sapi_contrib::jsonnet
sapi::sapi
)

View File

@ -15,7 +15,7 @@
#include <cstdlib>
#include <iostream>
#include "jsonnet_base_sandbox.h" // NOLINT(build/include)
#include "contrib/jsonnet/jsonnet_base_sandbox.h"
#include "sandboxed_api/util/fileops.h"
#include "sandboxed_api/util/path.h"

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
#include "jsonnet_base_transaction.h" // NOLINT(build/include)
#include "contrib/jsonnet/jsonnet_base_transaction.h"
#include "sandboxed_api/util/fileops.h"
#include "sandboxed_api/util/path.h"

View File

@ -19,7 +19,6 @@
#include <iostream>
#include "jsonnet_sapi.sapi.h" // NOLINT(build/include)
#include "sandboxed_api/util/flag.h"
#include "sandboxed_api/util/fileops.h"
#include "sandboxed_api/util/path.h"

View File

@ -19,7 +19,6 @@
#include <iostream>
#include "jsonnet_sapi.sapi.h" // NOLINT(build/include)
#include "sandboxed_api/util/flag.h"
#include "sandboxed_api/util/fileops.h"
#include "sandboxed_api/util/path.h"

View File

@ -15,7 +15,7 @@
#include <cstdlib>
#include <iostream>
#include "jsonnet_base_sandbox.h" // NOLINT(build/include)
#include "contrib/jsonnet/jsonnet_base_sandbox.h"
#include "sandboxed_api/util/fileops.h"
#include "sandboxed_api/util/path.h"

View File

@ -20,7 +20,7 @@
#include <vector>
-#include "utils.h"
+#include "jsonnet_helper.h" // NOLINT(build/include)
+#include "contrib/jsonnet/jsonnet_helper.h"
-extern "C" {
-#include <libjsonnet.h>

View File

@ -23,7 +23,6 @@
#include <utility>
#include "jsonnet_sapi.sapi.h" // NOLINT(build/include)
#include "sandboxed_api/util/flag.h"
#include "sandboxed_api/transaction.h"
#include "sandboxed_api/vars.h"
@ -33,7 +32,7 @@ class JsonnetBaseSandbox : public JsonnetSandbox {
: in_file_(std::move(in_file)), out_file_(std::move(out_file)) {}
std::unique_ptr<sandbox2::Policy> ModifyPolicy(
sandbox2::PolicyBuilder *) override {
sandbox2::PolicyBuilder*) override {
return sandbox2::PolicyBuilder()
.AllowStaticStartup()
.AllowOpen()

View File

@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
#include "jsonnet_helper.h" // NOLINT(build/include)
#include "contrib/jsonnet/jsonnet_helper.h"
#include <cstring>

View File

@ -12,17 +12,18 @@
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef CONTRIB_JSONNET_HELPER_H_
#define CONTRIB_JSONNET_HELPER_H_
#ifndef CONTRIB_JSONNET_JSONNET_HELPER_H_
#define CONTRIB_JSONNET_JSONNET_HELPER_H_
extern "C" {
#include <libjsonnet.h> // NOLINT(build/include)
#include <libjsonnet_fmt.h> // NOLINT(build/include)
#include <libjsonnet.h>
#include <libjsonnet_fmt.h>
}
#include "jsonnet/cmd/utils.h" // NOLINT(build/include)
extern "C" {
struct JsonnetVm* c_jsonnet_make(void);
void c_jsonnet_destroy(struct JsonnetVm* vm);
@ -60,4 +61,4 @@ char* c_jsonnet_fmt_snippet(struct JsonnetVm* vm, const char* filename,
const char* snippet, int* error);
}
#endif // CONTRIB_JSONNET_HELPER_H_
#endif // CONTRIB_JSONNET_JSONNET_HELPER_H_

View File

@ -20,10 +20,8 @@
#include <streambuf>
#include <string>
#include "jsonnet_base_sandbox.h" // NOLINT(build/include)
#include "jsonnet_sapi.sapi.h" // NOLINT(build/include)
#include "gtest/gtest.h"
#include "sandboxed_api/util/flag.h"
#include "contrib/jsonnet/jsonnet_base_sandbox.h"
#include "sandboxed_api/util/path.h"
#include "sandboxed_api/util/status_matchers.h"