use of jenkins.scm.api.SCMRevision in project gitea-plugin by jenkinsci.
the class GiteaPullSCMEvent method headsFor.
/**
* {@inheritDoc}
*/
@NonNull
@Override
public Map<SCMHead, SCMRevision> headsFor(GiteaSCMSource source) {
Map<SCMHead, SCMRevision> result = new HashMap<>();
try (GiteaSCMSourceRequest request = new GiteaSCMSourceContext(null, SCMHeadObserver.none()).withTraits(source.getTraits()).newRequest(source, null)) {
if (!request.isFetchPRs()) {
return result;
}
final GiteaPullRequest p = getPayload().getPullRequest();
if (p == null) {
// the pull request has been deleted, sadly we have no way to determine where the PR was from
// so we just blast hit with all potential cases and using dummy values.
// the values are not important as the event consumers will be matching on SCMHead.getName()
// and so will see that there is a new "head" for the old name, reconfirm the revision
// and find that the head no longer exists... and our job is done!
Set<ChangeRequestCheckoutStrategy> strategies = EnumSet.noneOf(ChangeRequestCheckoutStrategy.class);
if (request.isFetchForkPRs()) {
strategies.addAll(request.getForkPRStrategies());
}
if (request.isFetchOriginPRs()) {
strategies.addAll(request.getOriginPRStrategies());
}
for (ChangeRequestCheckoutStrategy strategy : strategies) {
result.put(new PullRequestSCMHead("PR-" + getPayload().getNumber() + (strategies.size() > 1 ? "-" + strategy.name().toLowerCase(Locale.ENGLISH) : ""), getPayload().getNumber(), new BranchSCMHead("dummy-name"), ChangeRequestCheckoutStrategy.MERGE, SCMHeadOrigin.DEFAULT, source.getRepoOwner(), source.getRepository(), "dummy-name"), null);
}
} else {
String originOwner = p.getHead().getRepo().getOwner().getUsername();
String originRepository = p.getHead().getRepo().getName();
Set<ChangeRequestCheckoutStrategy> strategies = request.getPRStrategies(!StringUtils.equalsIgnoreCase(source.getRepoOwner(), originOwner) && StringUtils.equalsIgnoreCase(source.getRepository(), originRepository));
for (ChangeRequestCheckoutStrategy strategy : strategies) {
PullRequestSCMHead h = new PullRequestSCMHead("PR-" + p.getNumber() + (strategies.size() > 1 ? "-" + strategy.name().toLowerCase(Locale.ENGLISH) : ""), p.getNumber(), new BranchSCMHead(p.getBase().getRef()), strategy, StringUtils.equalsIgnoreCase(originOwner, source.getRepoOwner()) && StringUtils.equalsIgnoreCase(originRepository, source.getRepository()) ? SCMHeadOrigin.DEFAULT : new SCMHeadOrigin.Fork(originOwner + "/" + originRepository), originOwner, originRepository, p.getHead().getRef());
result.put(h, getPayload().getAction() == GiteaPullRequestEventType.CLOSED ? null : new PullRequestSCMRevision(h, new BranchSCMRevision(h.getTarget(), p.getBase().getSha()), new BranchSCMRevision(new BranchSCMHead(h.getOriginName()), p.getHead().getSha())));
}
}
} catch (IOException e) {
// ignore
}
return result;
}
use of jenkins.scm.api.SCMRevision in project gitea-plugin by jenkinsci.
the class GiteaSCMSource method retrieve.
@Override
protected void retrieve(SCMSourceCriteria criteria, @NonNull SCMHeadObserver observer, SCMHeadEvent<?> event, @NonNull final TaskListener listener) throws IOException, InterruptedException {
try (GiteaConnection c = gitea().open()) {
listener.getLogger().format("Looking up repository %s/%s%n", repoOwner, repository);
giteaRepository = c.fetchRepository(repoOwner, repository);
sshRemote = giteaRepository.getSshUrl();
if (giteaRepository.isEmpty()) {
listener.getLogger().format("Repository %s is empty%n", repository);
return;
}
try (GiteaSCMSourceRequest request = new GiteaSCMSourceContext(criteria, observer).withTraits(getTraits()).newRequest(this, listener)) {
request.setConnection(c);
if (request.isFetchBranches()) {
request.setBranches(c.fetchBranches(giteaRepository));
}
if (request.isFetchPRs()) {
if (giteaRepository.isMirror()) {
listener.getLogger().format("%n Ignoring pull requests as repository is a mirror...%n");
} else {
request.setPullRequests(c.fetchPullRequests(giteaRepository));
}
}
if (request.isFetchBranches()) {
int count = 0;
listener.getLogger().format("%n Checking branches...%n");
for (final GiteaBranch b : c.fetchBranches(giteaRepository)) {
count++;
listener.getLogger().format("%n Checking branch %s%n", HyperlinkNote.encodeTo(UriTemplate.buildFromTemplate(giteaRepository.getHtmlUrl()).literal("/src").path("branch").build().set("branch", b.getName()).expand(), b.getName()));
if (request.process(new BranchSCMHead(b.getName()), new SCMSourceRequest.RevisionLambda<BranchSCMHead, BranchSCMRevision>() {
@NonNull
@Override
public BranchSCMRevision create(@NonNull BranchSCMHead head) throws IOException, InterruptedException {
return new BranchSCMRevision(head, b.getCommit().getId());
}
}, new SCMSourceRequest.ProbeLambda<BranchSCMHead, BranchSCMRevision>() {
@NonNull
@Override
public SCMSourceCriteria.Probe create(@NonNull BranchSCMHead head, @Nullable BranchSCMRevision revision) throws IOException, InterruptedException {
return createProbe(head, revision);
}
}, new SCMSourceRequest.Witness() {
@Override
public void record(@NonNull SCMHead head, SCMRevision revision, boolean isMatch) {
if (isMatch) {
listener.getLogger().format(" Met criteria%n");
} else {
listener.getLogger().format(" Does not meet criteria%n");
}
}
})) {
listener.getLogger().format("%n %d branches were processed (query completed)%n", count);
return;
}
}
listener.getLogger().format("%n %d branches were processed%n", count);
}
if (request.isFetchPRs() && !giteaRepository.isMirror() && !(request.getForkPRStrategies().isEmpty() && request.getOriginPRStrategies().isEmpty())) {
int count = 0;
listener.getLogger().format("%n Checking pull requests...%n");
for (final GiteaPullRequest p : c.fetchPullRequests(giteaRepository, EnumSet.of(GiteaIssueState.OPEN))) {
if (p == null) {
continue;
}
count++;
listener.getLogger().format("%n Checking pull request %s%n", HyperlinkNote.encodeTo(UriTemplate.buildFromTemplate(giteaRepository.getHtmlUrl()).literal("/pulls").path("number").build().set("number", p.getNumber()).expand(), "#" + p.getNumber()));
String originOwner = p.getHead().getRepo().getOwner().getUsername();
String originRepository = p.getHead().getRepo().getName();
Set<ChangeRequestCheckoutStrategy> strategies = request.getPRStrategies(!StringUtils.equalsIgnoreCase(repoOwner, originOwner) && StringUtils.equalsIgnoreCase(repository, originRepository));
for (ChangeRequestCheckoutStrategy strategy : strategies) {
if (request.process(new PullRequestSCMHead("PR-" + p.getNumber() + (strategies.size() > 1 ? "-" + strategy.name().toLowerCase(Locale.ENGLISH) : ""), p.getNumber(), new BranchSCMHead(p.getBase().getRef()), strategy, StringUtils.equalsIgnoreCase(originOwner, repoOwner) && StringUtils.equalsIgnoreCase(originRepository, repository) ? SCMHeadOrigin.DEFAULT : new SCMHeadOrigin.Fork(originOwner + "/" + originRepository), originOwner, originRepository, p.getHead().getRef()), new SCMSourceRequest.RevisionLambda<PullRequestSCMHead, PullRequestSCMRevision>() {
@NonNull
@Override
public PullRequestSCMRevision create(@NonNull PullRequestSCMHead head) throws IOException, InterruptedException {
return new PullRequestSCMRevision(head, new BranchSCMRevision(head.getTarget(), p.getBase().getSha()), new BranchSCMRevision(new BranchSCMHead(head.getOriginName()), p.getHead().getSha()));
}
}, new SCMSourceRequest.ProbeLambda<PullRequestSCMHead, PullRequestSCMRevision>() {
@NonNull
@Override
public SCMSourceCriteria.Probe create(@NonNull PullRequestSCMHead h, @Nullable PullRequestSCMRevision r) throws IOException, InterruptedException {
return createProbe(h, r);
}
}, new SCMSourceRequest.Witness() {
@Override
public void record(@NonNull SCMHead head, SCMRevision revision, boolean isMatch) {
if (isMatch) {
listener.getLogger().format(" Met criteria%n");
} else {
listener.getLogger().format(" Does not meet criteria%n");
}
}
})) {
listener.getLogger().format("%n %d pull requests were processed (query completed)%n", count);
return;
}
}
}
listener.getLogger().format("%n %d pull requests were processed%n", count);
}
}
}
}
use of jenkins.scm.api.SCMRevision in project gitea-plugin by jenkinsci.
the class GiteaSCMBuilder method build.
/**
* {@inheritDoc}
*/
@NonNull
@Override
public GitSCM build() {
final SCMHead h = head();
final SCMRevision r = revision();
try {
withGiteaRemote();
if (h instanceof PullRequestSCMHead) {
PullRequestSCMHead head = (PullRequestSCMHead) h;
if (head.getCheckoutStrategy() == ChangeRequestCheckoutStrategy.MERGE) {
// add the target branch to ensure that the revision we want to merge is also available
String name = head.getTarget().getName();
String localName = "remotes/" + remoteName() + "/" + name;
Set<String> localNames = new HashSet<>();
boolean match = false;
String targetSrc = Constants.R_HEADS + name;
String targetDst = Constants.R_REMOTES + remoteName() + "/" + name;
for (RefSpec b : asRefSpecs()) {
String dst = b.getDestination();
assert dst.startsWith(Constants.R_REFS) : "All git references must start with refs/";
if (targetSrc.equals(b.getSource())) {
if (targetDst.equals(dst)) {
match = true;
} else {
// pick up the configured destination name
localName = dst.substring(Constants.R_REFS.length());
match = true;
}
} else {
localNames.add(dst.substring(Constants.R_REFS.length()));
}
}
if (!match) {
if (localNames.contains(localName)) {
// conflict with intended name
localName = "remotes/" + remoteName() + "/upstream-" + name;
}
if (localNames.contains(localName)) {
// conflict with intended alternative name
localName = "remotes/" + remoteName() + "/pr-" + head.getId() + "-upstream-" + name;
}
if (localNames.contains(localName)) {
// ok we're just going to mangle our way to something that works
Random entropy = new Random();
while (localNames.contains(localName)) {
localName = "remotes/" + remoteName() + "/pr-" + head.getId() + "-upstream-" + name + "-" + Integer.toHexString(entropy.nextInt(Integer.MAX_VALUE));
}
}
withRefSpec("+refs/heads/" + name + ":refs/" + localName);
}
withExtension(new MergeWithGitSCMExtension(localName, r instanceof PullRequestSCMRevision ? ((BranchSCMRevision) ((PullRequestSCMRevision) r).getTarget()).getHash() : null));
}
if (r instanceof PullRequestSCMRevision) {
withRevision(((PullRequestSCMRevision) r).getOrigin());
}
}
return super.build();
} finally {
withHead(h);
withRevision(r);
}
}
use of jenkins.scm.api.SCMRevision in project gitea-plugin by jenkinsci.
the class GiteaNotifier method sendNotifications.
/**
* Sends notifications to Bitbucket on Checkout (for the "In Progress" Status).
*/
private static void sendNotifications(Run<?, ?> build, TaskListener listener) throws IOException, InterruptedException {
final SCMSource s = SCMSource.SourceByItem.findSource(build.getParent());
if (!(s instanceof GiteaSCMSource)) {
return;
}
GiteaSCMSource source = (GiteaSCMSource) s;
if (new GiteaSCMSourceContext(null, SCMHeadObserver.none()).withTraits(source.getTraits()).notificationsDisabled()) {
return;
}
String url;
try {
url = DisplayURLProvider.get().getRunURL(build);
} catch (IllegalStateException e) {
listener.getLogger().println("Can not determine Jenkins root URL. Commit status notifications are disabled until a root URL is" + " configured in Jenkins global configuration.");
return;
}
Result result = build.getResult();
GiteaCommitStatus status = new GiteaCommitStatus();
status.setTargetUrl(url);
status.setContext(build.getParent().getFullName());
if (Result.SUCCESS.equals(result)) {
status.setDescription("This commit looks good");
status.setState(GiteaCommitState.SUCCESS);
} else if (Result.UNSTABLE.equals(result)) {
status.setDescription("This commit has test failures");
status.setState(GiteaCommitState.FAILURE);
} else if (Result.FAILURE.equals(result)) {
status.setDescription("There was a failure building this commit");
status.setState(GiteaCommitState.FAILURE);
} else if (result != null) {
// ABORTED etc.
status.setDescription("Something is wrong with the build of this commit");
status.setState(GiteaCommitState.ERROR);
} else {
status.setDescription("Build started...");
status.setState(GiteaCommitState.PENDING);
}
SCMRevision revision = SCMRevisionAction.getRevision(source, build);
String hash;
if (revision instanceof BranchSCMRevision) {
listener.getLogger().format("[Gitea] Notifying branch build status: %s %s%n", status.getState().name(), status.getDescription());
hash = ((BranchSCMRevision) revision).getHash();
} else if (revision instanceof PullRequestSCMRevision) {
listener.getLogger().format("[Gitea] Notifying pull request build status: %s %s%n", status.getState().name(), status.getDescription());
hash = ((PullRequestSCMRevision) revision).getOrigin().getHash();
} else {
// TODO tags
return;
}
JobScheduledListener jsl = ExtensionList.lookup(QueueListener.class).get(JobScheduledListener.class);
if (jsl != null) {
// we are setting the status, so don't let the queue listener background thread change it to pending
synchronized (jsl.resolving) {
jsl.resolving.remove(build.getParent());
}
}
try (GiteaConnection c = source.gitea().open()) {
int tries = 3;
while (true) {
tries--;
try {
c.createCommitStatus(source.getRepoOwner(), source.getRepository(), hash, status);
break;
} catch (GiteaHttpStatusException e) {
if (e.getStatusCode() == 500 && tries > 0) {
// server may be overloaded
continue;
}
throw e;
}
}
listener.getLogger().format("[Gitea] Notified%n");
}
}
Aggregations