• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

jreleaser / jreleaser / #525

01 Aug 2025 09:22PM UTC coverage: 49.229% (+0.8%) from 48.454%
#525

push

github

aalmiray
fix(gradle): Remove usages of ConfigureUtil

Fixes #1956

26274 of 53371 relevant lines covered (49.23%)

0.49 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

97.75
/core/jreleaser-engine/src/main/java/org/jreleaser/engine/schema/JsonSchemaGenerator.java
1
/*
2
 * SPDX-License-Identifier: Apache-2.0
3
 *
4
 * Copyright 2020-2025 The JReleaser authors.
5
 *
6
 * Licensed under the Apache License, Version 2.0 (the "License");
7
 * you may not use this file except in compliance with the License.
8
 * You may obtain a copy of the License at
9
 *
10
 *     https://www.apache.org/licenses/LICENSE-2.0
11
 *
12
 * Unless required by applicable law or agreed to in writing, software
13
 * distributed under the License is distributed on an "AS IS" BASIS,
14
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
 * See the License for the specific language governing permissions and
16
 * limitations under the License.
17
 */
18
package org.jreleaser.engine.schema;
19

20
import com.fasterxml.classmate.ResolvedType;
21
import com.fasterxml.jackson.databind.JsonNode;
22
import com.fasterxml.jackson.databind.SerializationFeature;
23
import com.github.victools.jsonschema.generator.Option;
24
import com.github.victools.jsonschema.generator.OptionPreset;
25
import com.github.victools.jsonschema.generator.SchemaGenerationContext;
26
import com.github.victools.jsonschema.generator.SchemaGenerator;
27
import com.github.victools.jsonschema.generator.SchemaGeneratorConfig;
28
import com.github.victools.jsonschema.generator.SchemaGeneratorConfigBuilder;
29
import com.github.victools.jsonschema.generator.SchemaVersion;
30
import com.github.victools.jsonschema.generator.impl.DefinitionKey;
31
import com.github.victools.jsonschema.generator.naming.DefaultSchemaDefinitionNamingStrategy;
32
import com.github.victools.jsonschema.module.jackson.JacksonModule;
33
import org.jreleaser.model.JReleaserException;
34
import org.jreleaser.model.JReleaserVersion;
35
import org.jreleaser.model.internal.JReleaserModel;
36
import org.jreleaser.model.internal.announce.Announce;
37
import org.jreleaser.model.internal.announce.HttpAnnouncer;
38
import org.jreleaser.model.internal.announce.WebhookAnnouncer;
39
import org.jreleaser.model.internal.download.AbstractSshDownloader;
40
import org.jreleaser.model.internal.download.FtpDownloader;
41
import org.jreleaser.model.internal.download.HttpDownloader;
42
import org.jreleaser.model.internal.upload.AbstractSshUploader;
43
import org.jreleaser.model.internal.upload.ArtifactoryUploader;
44
import org.jreleaser.model.internal.upload.FtpUploader;
45
import org.jreleaser.model.internal.upload.HttpUploader;
46

47
import java.io.PrintWriter;
48
import java.nio.file.Files;
49
import java.nio.file.Path;
50
import java.nio.file.Paths;
51
import java.util.LinkedHashMap;
52
import java.util.Map;
53

54
import static java.nio.charset.StandardCharsets.UTF_8;
55
import static java.nio.file.StandardOpenOption.CREATE;
56
import static java.nio.file.StandardOpenOption.TRUNCATE_EXISTING;
57
import static java.nio.file.StandardOpenOption.WRITE;
58
import static java.util.Collections.singletonMap;
59
import static org.jreleaser.bundle.RB.$;
60

61
/**
62
 * @author Andres Almiray
63
 * @since 1.4.0
64
 */
65
public final class JsonSchemaGenerator {
66
    private JsonSchemaGenerator() {
67
        // noop
68
    }
69

70
    public static void generate(PrintWriter out) {
71
        Map<String, String> mappings = new LinkedHashMap<>();
1✔
72
        mappings.put("Map<String, Object>", "Properties");
1✔
73
        mappings.put("Map<String, String>", "StringProperties");
1✔
74
        mappings.put("Map<String, WebhookAnnouncer>", "WebhookAnnouncerMap");
1✔
75
        mappings.put("Map<String, HttpAnnouncer>", "HttpAnnouncerMap");
1✔
76
        mappings.put("Map<String, ArchiveAssembler>", "ArchiveAssemblerMap");
1✔
77
        mappings.put("Map<String, JavaArchiveAssembler>", "JavaArchiveAssemblerMap");
1✔
78
        mappings.put("Map<String, JlinkAssembler>", "JlinkAssemblerMap");
1✔
79
        mappings.put("Map<String, JpackageAssembler>", "JpackageAssemblerMap");
1✔
80
        mappings.put("Map<String, NativeImageAssembler>", "NativeImageAssemblerMap");
1✔
81
        mappings.put("Map<String, Distribution>", "DistributionMap");
1✔
82
        mappings.put("Map<String, DockerSpec>", "DockerSpecMap");
1✔
83
        mappings.put("Map<String, JibSpec>", "JibSpecMap");
1✔
84
        mappings.put("Map<String, ArtifactoryUploader>", "ArtifactoryUploaderMap");
1✔
85
        mappings.put("Map<String, ForgejoUploader>", "ForgejoUploaderMap");
1✔
86
        mappings.put("Map<String, GiteaUploader>", "GiteaUploaderMap");
1✔
87
        mappings.put("Map<String, GitlabUploader>", "GitlabUploaderMap");
1✔
88
        mappings.put("Map<String, FtpUploader>", "FtpUploaderMap");
1✔
89
        mappings.put("Map<String, HttpUploader>", "HttpUploaderMap");
1✔
90
        mappings.put("Map<String, SftpUploader>", "SftpUploaderMap");
1✔
91
        mappings.put("Map<String, ScpUploader>", "ScpUploaderMap");
1✔
92
        mappings.put("Map<String, S3Uploader>", "S3UploaderMap");
1✔
93
        mappings.put("Map<String, FtpDownloader>", "FtpDownloaderMap");
1✔
94
        mappings.put("Map<String, HttpDownloader>", "HttpDownloaderMap");
1✔
95
        mappings.put("Map<String, SftpDownloader>", "SftpDownloaderMap");
1✔
96
        mappings.put("Map<String, ScpDownloader>", "ScpDownloaderMap");
1✔
97
        mappings.put("Map<String, Extension>", "ExtensionMap");
1✔
98
        mappings.put("Map<String, ArtifactoryMavenDeployer>", "ArtifactoryMavenDeployerMap");
1✔
99
        mappings.put("Map<String, AzureMavenDeployer>", "AzureMavenDeployerMap");
1✔
100
        mappings.put("Map<String, ForgejoMavenDeployer>", "ForgejoMavenDeployerMap");
1✔
101
        mappings.put("Map<String, GiteaMavenDeployer>", "GiteaMavenDeployerMap");
1✔
102
        mappings.put("Map<String, GithubMavenDeployer>", "GithubMavenDeployerMap");
1✔
103
        mappings.put("Map<String, GitlabMavenDeployer>", "GitlabMavenDeployerMap");
1✔
104
        mappings.put("Map<String, Nexus2MavenDeployer>", "Nexus2MavenDeployerMap");
1✔
105
        mappings.put("Map<String, Nexus3MavenDeployer>", "Nexus3MavenDeployerMap");
1✔
106
        mappings.put("Map<String, MavenCentralMavenDeployer>", "MavenCentralMavenDeployerMap");
1✔
107
        mappings.put("Map<String, SwidTag>", "SwidTagMap");
1✔
108
        mappings.put("Map<String, NamedCommandHooks>", "NamedCommandHooksMap");
1✔
109
        mappings.put("Map<String, NamedScriptHooks>", "NamedScriptHooksMap");
1✔
110
        mappings.put("Map<String, NamedJbangHooks>", "NamedJbangHooksMap");
1✔
111

112
        try {
113
            SchemaGeneratorConfigBuilder configBuilder = new SchemaGeneratorConfigBuilder(SchemaVersion.DRAFT_7, OptionPreset.PLAIN_JSON);
1✔
114
            configBuilder.getObjectMapper().enable(SerializationFeature.INDENT_OUTPUT);
1✔
115
            configBuilder.with(Option.SCHEMA_VERSION_INDICATOR);
1✔
116
            configBuilder.with(Option.FORBIDDEN_ADDITIONAL_PROPERTIES_BY_DEFAULT);
1✔
117
            configBuilder.with(Option.DEFINITION_FOR_MAIN_SCHEMA);
1✔
118
            configBuilder.with(Option.DEFINITIONS_FOR_ALL_OBJECTS);
1✔
119
            configBuilder.with(Option.MAP_VALUES_AS_ADDITIONAL_PROPERTIES);
1✔
120
            configBuilder.with(Option.GETTER_METHODS);
1✔
121
            configBuilder.with(Option.NONSTATIC_NONVOID_NONGETTER_METHODS);
1✔
122
            configBuilder.with(Option.FIELDS_DERIVED_FROM_ARGUMENTFREE_METHODS);
1✔
123
            configBuilder.with(Option.STRICT_TYPE_INFO);
1✔
124
            JacksonModule jacksonModule = new JacksonModule();
1✔
125
            configBuilder.with(jacksonModule);
1✔
126
            configBuilder.forTypesInGeneral()
1✔
127
                .withDescriptionResolver(scope -> scope.getType().getErasedType() == JReleaserModel.class ?
1✔
128
                    String.format("JReleaser %s", JReleaserVersion.getPlainVersion()) : null)
1✔
129
                .withPatternPropertiesResolver(scope -> {
1✔
130
                    if (scope.getType().isInstanceOf(Map.class)) {
1✔
131
                        ResolvedType type = scope.getTypeParameterFor(Map.class, 1);
1✔
132
                        if (type.getErasedType() != String.class && type.getErasedType() != Object.class) {
1✔
133
                            return singletonMap("^[a-zA-Z][a-zA-Z0-9-]*[a-zA-Z0-9]?$", type);
1✔
134
                        }
135
                    }
136
                    return null;
1✔
137
                })
138
                .withAdditionalPropertiesResolver(scope -> {
1✔
139
                    if (scope.getType().isInstanceOf(Map.class)) {
1✔
140
                        ResolvedType type = scope.getTypeParameterFor(Map.class, 1);
1✔
141
                        if (type.getErasedType() == String.class || type.getErasedType() == Object.class) {
1✔
142
                            return scope.getTypeParameterFor(Map.class, 0);
1✔
143
                        }
144
                    }
145
                    return null;
1✔
146
                })
147
                .withDefinitionNamingStrategy(new DefaultSchemaDefinitionNamingStrategy() {
1✔
148
                    @Override
149
                    public String getDefinitionNameForKey(DefinitionKey key, SchemaGenerationContext context) {
150
                        String definitionNameForKey = super.getDefinitionNameForKey(key, context);
1✔
151
                        return mappings.getOrDefault(definitionNameForKey, definitionNameForKey);
1✔
152
                    }
153
                });
154
            configBuilder.forMethods()
1✔
155
                .withIgnoreCheck(method -> {
1✔
156
                    if (method.isVoid() || !method.getName().startsWith("get") || method.getArgumentCount() != 0) {
1✔
157
                        return true;
1✔
158
                    }
159
                    Class<?> declaringType = method.getDeclaringType().getErasedType();
1✔
160
                    return declaringType != Announce.class &&
1✔
161
                        declaringType != HttpAnnouncer.class &&
162
                        declaringType != HttpDownloader.class &&
163
                        declaringType != HttpUploader.class &&
164
                        declaringType != ArtifactoryUploader.class &&
165
                        declaringType != FtpDownloader.class &&
166
                        declaringType != FtpUploader.class &&
167
                        declaringType != AbstractSshDownloader.class &&
168
                        declaringType != AbstractSshUploader.class &&
169
                        declaringType != WebhookAnnouncer.class;
170
                });
171

172
            SchemaGeneratorConfig config = configBuilder.build();
1✔
173
            SchemaGenerator generator = new SchemaGenerator(config);
1✔
174
            JsonNode jsonSchema = generator.generateSchema(JReleaserModel.class);
1✔
175

176
            String fileName = String.format("jreleaser-schema-%s.json", JReleaserVersion.getPlainVersion());
1✔
177
            Path schemaPath = Paths.get(fileName);
1✔
178
            String json = configBuilder.getObjectMapper().writeValueAsString(jsonSchema);
1✔
179
            Files.write(schemaPath, json.getBytes(UTF_8), CREATE, WRITE, TRUNCATE_EXISTING);
1✔
180
            out.println("Schema written to " + schemaPath.toAbsolutePath());
1✔
181
        } catch (Exception e) {
×
182
            throw new JReleaserException($("ERROR_unexpected_error"), e);
×
183
        }
1✔
184
    }
1✔
185
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc