use of com.google.copybara.exception.RepoException in project copybara by google.
the class GitRepository method showRef.
/**
* Execute show-ref git command in the local repository and returns a map from reference name to
* GitReference(SHA-1).
*/
protected ImmutableMap<String, GitRevision> showRef(Iterable<String> refs) throws RepoException {
ImmutableMap.Builder<String, GitRevision> result = ImmutableMap.builder();
CommandOutput commandOutput = gitAllowNonZeroExit(CommandRunner.NO_INPUT, ImmutableList.<String>builder().add("show-ref").addAll(refs).build());
if (!commandOutput.getStderr().isEmpty()) {
throw new RepoException(String.format("Error executing show-ref on %s git repo:\n%s", getGitDir(), commandOutput.getStderr()));
}
for (String line : Splitter.on('\n').split(commandOutput.getStdout())) {
if (line.isEmpty()) {
continue;
}
List<String> strings = Splitter.on(' ').splitToList(line);
Preconditions.checkState(strings.size() == 2 && SHA1_PATTERN.matcher(strings.get(0)).matches(), "Cannot parse line: '%s'", line);
// Ref -> SHA1
result.put(strings.get(1), new GitRevision(this, strings.get(0)));
}
return result.build();
}
use of com.google.copybara.exception.RepoException in project copybara by google.
the class GitRepository method lsRemote.
/**
* Runs a git ls-remote from the current directory for a repository url. Assumes the path to the
* git binary is already set. You don't have to be in a git repository to run this command. Does
* not work with remote names.
*
* @param url - see <repository> in git help ls-remote
* @param refs - see <refs> in git help ls-remote
* @param env - determines where the Git binaries are
* @param maxLogLines - Limit log lines to the number specified. -1 for unlimited
* @return - a map of refs to sha1 from the git ls-remote output.
*/
public static Map<String, String> lsRemote(String url, Collection<String> refs, Map<String, String> env, int maxLogLines) throws RepoException {
ImmutableMap.Builder<String, String> result = ImmutableMap.builder();
List<String> args = Lists.newArrayList("ls-remote", validateUrl(url));
args.addAll(refs);
CommandOutputWithStatus output;
try {
output = executeGit(FileSystems.getDefault().getPath("."), args, env, false, maxLogLines);
} catch (BadExitStatusWithOutputException e) {
throw new RepoException(String.format("Error running ls-remote for '%s' and refs '%s': Exit code %s, Output:\n%s", url, refs, e.getOutput().getTerminationStatus().getExitCode(), e.getOutput().getStderr()), e);
} catch (CommandException e) {
throw new RepoException(String.format("Error running ls-remote for '%s' and refs '%s'", url, refs), e);
}
if (output.getTerminationStatus().success()) {
for (String line : Splitter.on('\n').split(output.getStdout())) {
if (line.isEmpty()) {
continue;
}
Matcher matcher = LS_REMOTE_OUTPUT_LINE.matcher(line);
if (!matcher.matches()) {
throw new RepoException("Unexpected format for ls-remote output: " + line);
}
result.put(matcher.group(2), matcher.group(1));
}
}
return result.build();
}
use of com.google.copybara.exception.RepoException in project copybara by google.
the class GithubPROrigin method newReader.
@Override
public Reader<GitRevision> newReader(Glob originFiles, Authoring authoring) throws ValidationException {
return new ReaderImpl(url, originFiles, authoring, gitOptions, gitOriginOptions, generalOptions, /*includeBranchCommitLogs=*/
false, submoduleStrategy, firstParent) {
/**
* Disable rebase since this is controlled by useMerge field.
*/
@Override
protected void maybeRebase(GitRepository repo, GitRevision ref, Path workdir) throws RepoException, CannotResolveRevisionException {
}
@Override
public Optional<Baseline<GitRevision>> findBaseline(GitRevision startRevision, String label) throws RepoException, ValidationException {
if (!baselineFromBranch) {
return super.findBaseline(startRevision, label);
}
return findBaselinesWithoutLabel(startRevision, /*limit=*/
1).stream().map(e -> new Baseline<>(e.getSha1(), e)).findFirst();
}
@Override
public ImmutableList<GitRevision> findBaselinesWithoutLabel(GitRevision startRevision, int limit) throws RepoException, ValidationException {
String baseline = startRevision.associatedLabels().get(GITHUB_BASE_BRANCH_SHA1);
Preconditions.checkNotNull(baseline, "%s label should be present in %s", GITHUB_BASE_BRANCH_SHA1, startRevision);
GitRevision baselineRev = getRepository().resolveReference(baseline);
// Don't skip the first change as it is already the baseline
BaselinesWithoutLabelVisitor<GitRevision> visitor = new BaselinesWithoutLabelVisitor<>(originFiles, limit, /*skipFirst=*/
false);
visitChanges(baselineRev, visitor);
return visitor.getResult();
}
@Override
public Endpoint getFeedbackEndPoint() {
return new GitHubEndPoint(githubOptions, url);
}
/**
* Deal with the case of useMerge. We have a new commit (the merge) and first-parent from that
* commit doesn't work for this case.
*/
@Override
public ChangesResponse<GitRevision> changes(@Nullable GitRevision fromRef, GitRevision toRef) throws RepoException {
if (!useMerge) {
return super.changes(fromRef, toRef);
}
GitLogEntry merge = Iterables.getOnlyElement(getRepository().log(toRef.getSha1()).withLimit(1).run());
// Fast-forward merge
if (merge.getParents().size() == 1) {
return super.changes(fromRef, toRef);
}
// HEAD of the Pull Request
GitRevision gitRevision = merge.getParents().get(1);
ChangesResponse<GitRevision> prChanges = super.changes(fromRef, gitRevision);
// origin_files
if (prChanges.isEmpty()) {
return prChanges;
}
try {
return ChangesResponse.forChanges(ImmutableList.<Change<GitRevision>>builder().addAll(prChanges.getChanges()).add(change(merge.getCommit())).build());
} catch (EmptyChangeException e) {
throw new RepoException("Error getting the merge commit information: " + merge, e);
}
}
@Nullable
@Override
public String getGroupIdentity(GitRevision rev) throws RepoException {
return rev.associatedLabels().get(GITHUB_PR_NUMBER_LABEL);
}
};
}
use of com.google.copybara.exception.RepoException in project copybara by google.
the class GitCredential method fill.
/**
* Execute 'git credential fill' for a url
*
* @param cwd the directory to execute the command. This is important if credential configuration
* is set in the local git config.
* @param url url to get the credentials from
* @return a username and password
* @throws RepoException If the url doesn't have protocol (For example https://), the url is
* not valid or username/password couldn't be found
*/
public UserPassword fill(Path cwd, String url) throws RepoException, ValidationException {
Map<String, String> env = Maps.newHashMap(this.env);
// Prevent from asking user for the password (It goes directly to the terminal, not to the
// passed InputStream/OutputStream.
env.put("GIT_TERMINAL_PROMPT", "0");
URI uri;
try {
uri = URI.create(url);
} catch (IllegalArgumentException e) {
throw new ValidationException(e, "Cannot get credentials for " + url);
}
String protocol = uri.getScheme();
if (Strings.isNullOrEmpty(protocol)) {
throw new ValidationException("Cannot find the protocol for " + url);
}
String host = uri.getHost();
Command cmd = new Command(new String[] { gitBinary, "credential", "fill" }, env, cwd.toFile());
String request = String.format("protocol=%s\nhost=%s\n", protocol, host);
if (!Strings.isNullOrEmpty(uri.getPath())) {
request += String.format("path=%s\n", uri.getPath());
}
request += "\n";
ByteArrayOutputStream out = new ByteArrayOutputStream();
ByteArrayOutputStream err = new ByteArrayOutputStream();
try {
// DON'T REPLACE THIS WITH CommandRunner.execute(). WE DON'T WANT TO ACCIDENTALLY LOG THE
// PASSWORD!
CommandResult result = cmd.execute(new ByteArrayInputStream(request.getBytes(UTF_8)), new TimeoutKillableObserver(timeout.toMillis()), out, err);
if (!result.getTerminationStatus().success()) {
throw new RepoException("Error getting credentials:\n" + new String(err.toByteArray(), UTF_8));
}
} catch (BadExitStatusException e) {
String errStr = new String(err.toByteArray(), UTF_8);
if (errStr.contains("could not read")) {
throw new ValidationException("Interactive prompting of passwords for git is disabled," + " use git credential store before calling Copybara.");
}
throw new RepoException("Error getting credentials:\n" + errStr, e);
} catch (CommandException e) {
throw new RepoException("Error getting credentials", e);
}
Map<String, String> map = Splitter.on(NEW_LINE).omitEmptyStrings().withKeyValueSeparator("=").split(new String(out.toByteArray(), UTF_8));
if (!map.containsKey("username")) {
throw new RepoException("git credentials for " + url + " didn't return a username");
}
if (!map.containsKey("password")) {
throw new RepoException("git credentials for " + url + " didn't return a password");
}
return new UserPassword(map.get("username"), map.get("password"));
}
use of com.google.copybara.exception.RepoException in project copybara by google.
the class GitHubEndPoint method createStatus.
@SkylarkCallable(name = "create_status", doc = "Create or update a status for a commit. Returns the status created.", parameters = { @Param(name = "sha", type = String.class, named = true, doc = "The SHA-1 for which we want to create or update the status"), @Param(name = "state", type = String.class, named = true, doc = "The state of the commit status: 'success', 'error', 'pending' or 'failure'"), @Param(name = "context", type = String.class, doc = "The context for the commit" + " status. Use a value like 'copybara/import_successful' or similar", named = true), @Param(name = "description", type = String.class, named = true, doc = "Description about what happened"), @Param(name = "target_url", type = String.class, named = true, doc = "Url with expanded information about the event", noneable = true, defaultValue = "None") })
public Status createStatus(String sha, String state, String context, String description, Object targetUrl) throws EvalException {
try {
checkCondition(State.VALID_VALUES.contains(state), "Invalid value for state. Valid values: %s", State.VALID_VALUES);
checkCondition(GitRevision.COMPLETE_SHA1_PATTERN.matcher(sha).matches(), "Not a valid complete SHA-1: %s", sha);
checkCondition(!Strings.isNullOrEmpty(description), "description cannot be empty");
checkCondition(!Strings.isNullOrEmpty(context), "context cannot be empty");
String project = GithubUtil.getProjectNameFromUrl(url);
return githubOptions.getApi(project).createStatus(project, sha, new CreateStatusRequest(State.valueOf(state.toUpperCase()), convertFromNoneable(targetUrl, null), description, context));
} catch (RepoException | ValidationException e) {
throw new EvalException(/*location=*/
null, e);
}
}
Aggregations