diff --git a/pom.xml b/pom.xml index 0c67179..119241e 100644 --- a/pom.xml +++ b/pom.xml @@ -36,7 +36,7 @@ com.github.ArtemGet entrys - 0.4.0 + 0.4.1 com.github.ArtemGet diff --git a/src/main/java/io/github/artemget/tagrelease/Entrypoint.java b/src/main/java/io/github/artemget/tagrelease/Entrypoint.java index 955f510..c52f0cb 100644 --- a/src/main/java/io/github/artemget/tagrelease/Entrypoint.java +++ b/src/main/java/io/github/artemget/tagrelease/Entrypoint.java @@ -36,12 +36,14 @@ import io.github.artemget.tagrelease.command.CmdListServices; import io.github.artemget.tagrelease.command.CmdListServicesAll; import io.github.artemget.tagrelease.command.CmdListStands; +import io.github.artemget.tagrelease.command.CmdListServicesAllTags; import io.github.artemget.tagrelease.domain.Services; import io.github.artemget.tagrelease.domain.ServicesAll; import io.github.artemget.tagrelease.domain.Stands; import io.github.artemget.tagrelease.domain.StandsGl; import io.github.artemget.tagrelease.match.MatchAdmin; import io.github.artemget.tagrelease.match.MatchReply; +import io.github.artemget.teleroute.match.MatchAny; import io.github.artemget.teleroute.match.MatchRegex; import io.github.artemget.teleroute.route.RouteDfs; import io.github.artemget.teleroute.route.RouteFork; @@ -76,7 +78,7 @@ public static void main(final String[] args) throws EntryException, TelegramApiE new MatchAdmin(new ESplit(new EVal("bot.admins"))), new RouteDfs<>( new RouteFork<>( - new MatchRegex<>("[Э]эхо"), + new MatchRegex<>("[Ээ]хо"), new RouteFork<>( new MatchReply(), new CmdEchoReply(), @@ -96,7 +98,14 @@ public static void main(final String[] args) throws EntryException, TelegramApiE new CmdListStands(stands) ), new RouteFork<>( - new MatchRegex<>("[Сс]обери сервисы \\{([^{}]*)\\}\\s+префикс\\s+\\{([^{}]*)\\}$"), + new MatchRegex<>("[Пп]окажи тег \\{([^{}]*)\\}\\s+префикс\\s+\\{([^{}]*)\\}$"), + new CmdListServicesAllTags(host, project, token) + ), + new RouteFork<>( + new MatchAny<>( + new MatchRegex<>("[Сс]обери тег \\{([^{}]*)\\}\\s+префикс\\s+\\{([^{}]*)\\}$"), + new MatchRegex<>("[Сс]обери тег \\{([^{}]*)\\}\\s+префикс\\s+\\{([^{}]*)\\}\\s+ветка\\s+\\{([^{}]*)\\}$") + ), new CmdBuildTags(host, project, token) ) // new RouteFork<>( diff --git a/src/main/java/io/github/artemget/tagrelease/command/CmdBuildTags.java b/src/main/java/io/github/artemget/tagrelease/command/CmdBuildTags.java index f8d566a..ade9fd1 100644 --- a/src/main/java/io/github/artemget/tagrelease/command/CmdBuildTags.java +++ b/src/main/java/io/github/artemget/tagrelease/command/CmdBuildTags.java @@ -26,12 +26,13 @@ import io.github.artemget.entrys.Entry; import io.github.artemget.entrys.EntryException; +import io.github.artemget.entrys.fake.EFake; import io.github.artemget.entrys.operation.ESplit; -import io.github.artemget.entrys.operation.EUnwrap; import io.github.artemget.tagrelease.domain.Service; import io.github.artemget.tagrelease.domain.Services; import io.github.artemget.tagrelease.domain.ServicesAll; import io.github.artemget.tagrelease.domain.Tag; +import io.github.artemget.tagrelease.domain.TagEa; import io.github.artemget.tagrelease.domain.Tags; import io.github.artemget.tagrelease.domain.TagsGl; import io.github.artemget.tagrelease.exception.DomainException; @@ -69,27 +70,18 @@ public CmdBuildTags(final Services services, final Tags tags) { @Override public Send execute(Update update) throws CmdException { final List names; - final String branch; - final String prefix; final String[] values = StringUtils.substringsBetween(update.getMessage().getText(), "{", "}"); try { - names = new ESplit(new EUnwrap(values[0]), ",").value(); - } catch (final EntryException exception) { - throw new CmdException("Failed to parse service names for tag build", exception); - } - try { - prefix = new EUnwrap(values[1]).value(); + names = new ESplit(new EFake<>(values[0]), ",").value(); } catch (final EntryException exception) { - throw new CmdException("Failed to parse prefix name for tag build", exception); + throw new CmdException("Failed to parse service names for tag fetch", exception); } - try { - if (values.length >= 3) { - branch = new EUnwrap(values[2]).value(); - } else { - branch = "develop"; - } - } catch (final EntryException exception) { - throw new CmdException("Failed to parse branch name for tag build", exception); + final String prefix = values[1]; + final String branch; + if (values.length >= 3) { + branch = values[2]; + } else { + branch = "develop"; } final List succeed = new ArrayList<>(); final List failed = new ArrayList<>(); @@ -110,18 +102,28 @@ public Send execute(Update update) throws CmdException { failed.add(name); continue; } - succeed.add(tag); + succeed.add(new TagEa(service.name(), tag.name(), tag.branch(), tag.fromCommit(), tag.message(), tag.created())); } final SendMessage message = new SendMessage( update.getMessage().getChatId().toString(), - String.format( - "Собраны сервисы:\n%s\nОшибка сборки сервисов:\n%s", - new Tag.Printed(succeed).asString(), - String.join("\n", failed) - ) + String.format("Собраны сервисы:\n%s", new Tag.Printed(succeed).asString()) + .concat(CmdBuildTags.checked(failed)) ); message.setReplyToMessageId(update.getMessage().getMessageId()); message.enableMarkdownV2(true); return new SendMessageWrap<>(message); } + + private static String checked(List failed) { + final String message; + if (failed.isEmpty()) { + message = ""; + } else { + message = String.format( + "\nОшибка поиска тегов по сервисам:\n%s", + String.format("```\n%s\n```", String.join("\n", failed)) + ); + } + return message; + } } diff --git a/src/main/java/io/github/artemget/tagrelease/command/CmdListServicesAllTags.java b/src/main/java/io/github/artemget/tagrelease/command/CmdListServicesAllTags.java new file mode 100644 index 0000000..88a9e51 --- /dev/null +++ b/src/main/java/io/github/artemget/tagrelease/command/CmdListServicesAllTags.java @@ -0,0 +1,105 @@ +package io.github.artemget.tagrelease.command; + +import io.github.artemget.entrys.Entry; +import io.github.artemget.entrys.EntryException; +import io.github.artemget.entrys.fake.EFake; +import io.github.artemget.entrys.operation.ESplit; +import io.github.artemget.tagrelease.domain.Service; +import io.github.artemget.tagrelease.domain.Services; +import io.github.artemget.tagrelease.domain.ServicesAll; +import io.github.artemget.tagrelease.domain.Tag; +import io.github.artemget.tagrelease.domain.TagEa; +import io.github.artemget.tagrelease.domain.Tags; +import io.github.artemget.tagrelease.domain.TagsGl; +import io.github.artemget.tagrelease.exception.DomainException; +import io.github.artemget.teleroute.command.Cmd; +import io.github.artemget.teleroute.command.CmdException; +import io.github.artemget.teleroute.send.Send; +import io.github.artemget.teleroute.telegrambots.send.SendMessageWrap; +import java.util.ArrayList; +import java.util.List; +import org.apache.commons.lang3.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.telegram.telegrambots.meta.api.methods.send.SendMessage; +import org.telegram.telegrambots.meta.api.objects.Update; +import org.telegram.telegrambots.meta.bots.AbsSender; + +public class CmdListServicesAllTags implements Cmd { + private final Logger log = LoggerFactory.getLogger(CmdListServicesAllTags.class); + private final Services services; + private final Tags tags; + + public CmdListServicesAllTags( + final Entry host, + final Entry project, + final Entry token + ) { + this(new ServicesAll(host, project, token), new TagsGl(host, token)); + } + + public CmdListServicesAllTags(final Services services, final Tags tags) { + this.services = services; + this.tags = tags; + } + + @Override + public Send execute(Update update) throws CmdException { + final List names; + final String[] values = StringUtils.substringsBetween(update.getMessage().getText(), "{", "}"); + try { + names = new ESplit(new EFake<>(values[0]), ",").value(); + } catch (final EntryException exception) { + throw new CmdException("Failed to parse service names for tag fetch", exception); + } + final String prefix = values[1]; + final String branch; + if (values.length >= 3) { + branch = values[2]; + } else { + branch = "develop"; + } + final List succeed = new ArrayList<>(); + final List failed = new ArrayList<>(); + for (final String name : names) { + Service service; + try { + service = this.services.service(name); + } catch (final DomainException exception) { + log.error("Failed to fetch service:'{}' for tag build", name, exception); + failed.add(name); + continue; + } + final Tag tag; + try { + tag = this.tags.current(service.id(), branch, prefix); + } catch (final DomainException exception) { + log.error("Failed to fetch current tag for service:'{}'", name, exception); + failed.add(name); + continue; + } + succeed.add(new TagEa(service.name(), tag.name(), tag.branch(), tag.fromCommit(), tag.message(), tag.created())); + } + final SendMessage message = new SendMessage( + update.getMessage().getChatId().toString(), + String.format("Найдены теги:\n```\n%s\n```", new Tag.Printed(succeed).asString()) + .concat(CmdListServicesAllTags.checked(failed)) + ); + message.setReplyToMessageId(update.getMessage().getMessageId()); + message.enableMarkdownV2(true); + return new SendMessageWrap<>(message); + } + + private static String checked(List failed) { + final String message; + if (failed.isEmpty()) { + message = ""; + } else { + message = String.format( + "\nОшибка поиска тегов по сервисам:\n%s", + String.format("```\n%s\n```", String.join("\n", failed)) + ); + } + return message; + } +} diff --git a/src/main/java/io/github/artemget/tagrelease/domain/Tag.java b/src/main/java/io/github/artemget/tagrelease/domain/Tag.java index 288098f..990743f 100644 --- a/src/main/java/io/github/artemget/tagrelease/domain/Tag.java +++ b/src/main/java/io/github/artemget/tagrelease/domain/Tag.java @@ -57,7 +57,7 @@ public Printed(final List tags) { public String asString() { final StringBuilder string = new StringBuilder(); for (final Tag tag : this.tags) { - string.append(String.format("```%s:%s```\n", tag.repo(), tag.name())); + string.append(String.format("%s:%s\n", tag.repo(), tag.name())); } return string.toString(); } diff --git a/src/main/java/io/github/artemget/tagrelease/domain/TagsGl.java b/src/main/java/io/github/artemget/tagrelease/domain/TagsGl.java index 26e5cf0..2303c45 100644 --- a/src/main/java/io/github/artemget/tagrelease/domain/TagsGl.java +++ b/src/main/java/io/github/artemget/tagrelease/domain/TagsGl.java @@ -32,6 +32,8 @@ import io.github.artemget.tagrelease.entry.EFetchObj; import io.github.artemget.tagrelease.entry.EFunc; import io.github.artemget.tagrelease.exception.DomainException; +import java.net.URLEncoder; +import java.nio.charset.StandardCharsets; import javax.json.JsonArray; import javax.json.JsonObject; import javax.json.JsonValue; @@ -53,7 +55,7 @@ public TagsGl( new EFetchArr( new JdkRequest( String.format( - "%s/api/v4/projects/%s/repository/tags?search=%%5E%s", + "%s/api/v4/projects/%s/repository/tags?order_by=version&search=%%5E%s", url.value(), tag.repo(), tag.name().replace(".*", "") @@ -66,11 +68,12 @@ public TagsGl( new EFetchObj( new JdkRequest( String.format( - "%s/api/v4/projects/%s/repository/tags?ref=%s&tag_name=%s", + "%s/api/v4/projects/%s/repository/tags?ref=%s&tag_name=%s&message=%s", url.value(), tag.repo(), tag.branch(), - tag.name() + tag.name(), + tag.message() ) ).method(Request.POST) .header("Accept", "application/json") @@ -81,7 +84,8 @@ public TagsGl( int page = 1; boolean isFound = false; while (page <= 5 && !isFound) { - for (final JsonValue value : TagsGl.mrs(tag, url.value(), token.value(), String.valueOf(page))) { + final JsonArray mrs = TagsGl.mrs(tag, url.value(), token.value(), String.valueOf(page)); + for (final JsonValue value : mrs) { final JsonObject mr = value.asJsonObject(); final boolean isSquash = !mr.isNull("squash_commit_sha") && tag.fromCommit().equals(mr.getString("squash_commit_sha")); @@ -89,13 +93,19 @@ public TagsGl( && tag.fromCommit().equals(mr.getString("merge_commit_sha")); final boolean isMr = !mr.isNull("sha") && tag.fromCommit().equals(mr.getString("sha")); - if (isMerge && isSquash && isMr) { + if (isMerge || isSquash || isMr) { isFound = true; break; } - message.append(mr.getString("title")).append("\n\n"); - page++; + final String trimmed; + if (mr.getString("title").length() >= 30) { + trimmed = mr.getString("title").substring(0, 30).concat("..."); + } else { + trimmed = mr.getString("title"); + } + message.append(trimmed).append("\n"); } + page++; } return message.toString(); } @@ -116,15 +126,41 @@ public TagsGl( public Tag buildNew(final String serviceId, final String branch, final String prefix) throws DomainException { final Tag current = this.current(serviceId, branch, prefix); + final String next = TagsGl.next(current.name(), prefix); + String message; + try { + message = URLEncoder.encode( + String.format( + "Данное сообщение было сгенерировано автоматически.\nИзменения '%s' -> '%s':\n%s", + current.name(), + next, + this.message.apply(current) + ), + StandardCharsets.UTF_8 + ); + if (message.length() > 5000) { + message = message.substring(0, 4996).concat("\n..."); + } + } catch (final EntryException exception) { + message = ""; + log.error( + "Failed to fetch merge requests for service:'{}', branch:'{}'. Between tags '{}' - '{}'", + serviceId, + branch, + current.name(), + next, + exception + ); + } final JsonObject created; try { created = this.create.apply( new TagEa( current.repo(), - TagsGl.next(current.name(), prefix), + next, current.branch(), current.fromCommit(), - current.message(), + message, current.created() ) ); @@ -138,20 +174,6 @@ public Tag buildNew(final String serviceId, final String branch, final String pr ); } final JsonObject commit = created.getJsonObject("commit"); - String message; - try { - message = this.message.apply(current); - } catch (final EntryException exception) { - message = ""; - log.error( - "Failed to fetch merge requests for service:'{}', branch:'{}'. Between tags '{}' - '{}'", - serviceId, - branch, - current.name(), - created.getString("name"), - exception - ); - } return new TagEa( serviceId, created.getString("name"), @@ -170,14 +192,16 @@ public Tag current(final String serviceId, final String branch, final String pre response = this.tag.apply(new TagEa(serviceId, prefix, branch, "", "", "")); } catch (final EntryException exception) { throw new DomainException( - String.format( - "Failed to fetch tag with prefix:'%s' for service:'%s' from branch:'%s'", - prefix, serviceId, branch - ), + String.format("Failed to fetch tag with prefix:'%s' for service:'%s'", prefix, serviceId), exception ); } //TODO: add branch check + if (response.isEmpty()) { + throw new DomainException( + String.format("Failed to find tag with prefix:'%s' for service:'%s'", prefix, serviceId) + ); + } final JsonObject current = response.getJsonObject(0); final JsonObject commit = current.getJsonObject("commit"); return new TagEa( @@ -216,8 +240,8 @@ public static String next(final String current, final String prefix) { return next.toString(); } - private static JsonArray mrs(final Tag tag, String url, String token, String page) throws - EntryException { + private static JsonArray mrs(final Tag tag, String url, final String token, final String page) + throws EntryException { return new EFetchArr( new JdkRequest( String.format( @@ -229,7 +253,7 @@ private static JsonArray mrs(final Tag tag, String url, String token, String pag "20", page ) - ).method(Request.POST) + ).method(Request.GET) .header("Accept", "application/json") .header("PRIVATE-TOKEN", token) ).value();