Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 27 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,29 @@ Because permission management can be difficult, this plugin assumes you have
created an AWS CodeBuild project with the necessary IAM roles for the job
types that you will be running. The project can have any configuration; all
settings will be overridden by the plugin to provide a build using source
provided by the Jenkins host.
provided by the Jenkins host. However, it does expect you to have your own
custom `buildspec.yaml` file when creating the project. At runtime on building
your project, the plugin will override the buildspec and replace the following
variables that it expects to connect with the codebuilder jenkins slaves to build
the project. These variables are:

- `{CODEBUILD_JENKINS_URL}}`
- `{{CODEBUILD_COMPUTER_JNLP_MAC}}`
- `{{CODEBUILD_NODE_DISPLAY_NAME}}`

A sample buildspec might look like the following:

```yaml
version: 0.2
phases:
pre_build:
commands:
- which dockerd-entrypoint.sh >/dev/null && dockerd-entrypoint.sh || exit 0
build:
commands:
- jenkins-agent -noreconnect -workDir "$CODEBUILD_SRC_DIR" -url "{{CODEBUILD_JENKINS_URL}}" "{{CODEBUILD_COMPUTER_JNLP_MAC}}" "{{CODEBUILD_NODE_DISPLAY_NAME}}"
- exit 0
```

Once a project is created, you can configure the cloud in Jenkins by adding
a new cloud and configuring the plugin in `Manage Jenkins > Configure System`.
Expand Down Expand Up @@ -56,9 +78,12 @@ aws codebuild create-project \
--service-role jenkins-default \
--artifacts type=NO_ARTIFACTS \
--environment type=LINUX_CONTAINER,image=aws/codebuild/docker:18.09.0,computeType=BUILD_GENERAL1_SMALL \
--source $'type=NO_SOURCE,buildspec=version:0.2\nphases:\n build:\n commands:\n - exit 1'
--source $'type=NO_SOURCE,buildspec=version: 0.2\nphases:\n pre_build:\n commands:\n - which dockerd-entrypoint.sh >/dev/null && dockerd-entrypoint.sh || exit 0\n build:\n commands:\n - jenkins-agent -noreconnect -workDir "$CODEBUILD_SRC_DIR" -url "{{CODEBUILD_JENKINS_URL}}" "{{CODEBUILD_COMPUTER_JNLP_MAC}}" "{{CODEBUILD_NODE_DISPLAY_NAME}}"\n - exit 0\n'
```




#### Configuring the Plugin

In `Manage Jenkins > Configure System` you will find a drop-down to "Add a New
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
import com.amazonaws.services.codebuild.model.SourceType;
import com.amazonaws.services.codebuild.model.StartBuildRequest;
import com.amazonaws.services.codebuild.model.StartBuildResult;
import com.amazonaws.services.codebuild.model.BatchGetProjectsRequest;
import com.amazonaws.services.codebuild.model.BatchGetProjectsResult;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
Expand Down Expand Up @@ -64,8 +66,13 @@ public void launch(@Nonnull SlaveComputer computer, @Nonnull TaskListener listen

LOGGER.info("[CodeBuilder]: Launching {} with {}", computer, listener);
CodeBuilderComputer cbcpu = (CodeBuilderComputer) computer;

BatchGetProjectsResult projects = cloud.getClient().batchGetProjects(
new BatchGetProjectsRequest().withNames(cloud.getProjectName())
);
String existingBuildSpec = projects.getProjects().get(0).getSource().getBuildspec();
StartBuildRequest req = new StartBuildRequest().withProjectName(cloud.getProjectName())
.withSourceTypeOverride(SourceType.NO_SOURCE).withBuildspecOverride(buildspec(computer))
.withSourceTypeOverride(SourceType.NO_SOURCE).withBuildspecOverride(buildspec(existingBuildSpec, computer))
.withImageOverride(cloud.getJnlpImage()).withPrivilegedModeOverride(true)
.withComputeTypeOverride(cloud.getComputeType());

Expand Down Expand Up @@ -108,23 +115,18 @@ public void beforeDisconnect(@Nonnull SlaveComputer computer, @Nonnull StreamTas
}
}

private String buildspec(@Nonnull SlaveComputer computer) {
private String buildspec(String existingBuildSpec, @Nonnull SlaveComputer computer) {
Node n = computer.getNode();
if (n == null) {
return "";
}
String cmd = String.format("jenkins-agent -noreconnect -workDir \"$CODEBUILD_SRC_DIR\" -url \"%s\" \"%s\" \"%s\"",
cloud.getJenkinsUrl(), computer.getJnlpMac(), n.getDisplayName());
StringBuilder builder = new StringBuilder();
builder.append("version: 0.2\n");
builder.append("phases:\n");
builder.append(" pre_build:\n");
builder.append(" commands:\n");
builder.append(" - which dockerd-entrypoint.sh >/dev/null && dockerd-entrypoint.sh || exit 0\n");
builder.append(" build:\n");
builder.append(" commands:\n");
builder.append(" - " + cmd + " || exit 0\n");

return builder.toString();

// Reformat the buildspec with the variables:
// {{CODEBUILD_JENKINS_URL}}, {{CODEBUILD_COMPUTER_JNLP_MAC}} and {{CODEBUILD_NODE_DISPLAY_NAME}}
String newBuildSpec = existingBuildSpec
.replace("{{CODEBUILD_JENKINS_URL}}", cloud.getJenkinsUrl())
.replace("{{CODEBUILD_COMPUTER_JNLP_MAC}}", computer.getJnlpMac())
.replace("{{CODEBUILD_NODE_DISPLAY_NAME}}", n.getDisplayName());
return newBuildSpec;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ public class CodeBuilderCloudTest {

@Test
public void initializes_correctly() throws InterruptedException {
CodeBuilderCloud cloud = new CodeBuilderCloud(null, "project", null, null);
CodeBuilderCloud cloud = new CodeBuilderCloud(null, "project", null, "local");
assertEquals("project", cloud.getProjectName());
assertEquals("codebuilder_0", cloud.getDisplayName());
assertNotNull(cloud.getClient());
Expand Down