Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Gradle refactoring #319

Merged
merged 3 commits into from
Jun 12, 2024
Merged
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
2 changes: 1 addition & 1 deletion .github/workflows/gradle.yml
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ jobs:
java-version: 11
cache: gradle
- name: Run linters and test
run: ./gradlew test -PtestGradleVersion="${{ matrix.gradleVersion }}"
run: ./gradlew :plugin:test -PtestGradleVersion="${{ matrix.gradleVersion }}"
- name: Collect test results
if: ${{ failure() }}
uses: actions/upload-artifact@v4
Expand Down
11 changes: 5 additions & 6 deletions .github/workflows/node.yml
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ jobs:
matrix:
os: [ubuntu-latest]
directory: [
'tests/cpp', 'tests/dotnet', 'tests/duplicates', 'tests/go', 'tests/java', 'tests/js', 'tests/py_error'
'tests/dotnet', 'tests/duplicates', 'tests/go', 'tests/java', 'tests/js', 'tests/py_error' # 'tests/cpp',
]
arguments: ['']
pr: [ 'true', 'false' ]
Expand All @@ -122,6 +122,10 @@ jobs:
os: 'ubuntu-latest'
arguments: '-l,jetbrains/qodana-cdnet:2024.1-eap'
pr: 'false' # TODO: add true when pr-mode is available for dotnet-community
- directory: 'tests/cpp'
arguments: '-l,jetbrains/qodana-clang:2024.1-eap'
os: 'ubuntu-latest'
pr: 'false'
- directory: 'tests/java'
arguments: '-l,jetbrains/qodana-jvm-community'
os: 'ubuntu-latest'
Expand All @@ -146,11 +150,6 @@ jobs:
arguments: '-l,jetbrains/qodana-python-community'
os: 'ubuntu-latest'
pr: 'false'
exclude: # TODO: remove this block when pr-mode is available for clang
- directory: 'tests/cpp'
arguments: ''
os: 'ubuntu-latest'
pr: 'true'
steps:
- uses: actions/checkout@v4
with:
Expand Down
7 changes: 6 additions & 1 deletion .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,12 @@ jobs:
java-version: 11
cache: gradle
- name: Run linters and test
run: ./gradlew clean build publishPlugins -Pgradle.publish.key=${{ secrets.GRADLE_KEY }} -Pgradle.publish.secret=${{ secrets.GRADLE_TOKEN }} -PbuildNumber=${{ env.PATCH_VERSION }}
run: ./gradlew clean :plugin:build :plugin:publishPlugins -Pgradle.publish.key=${{ secrets.GRADLE_KEY }} -Pgradle.publish.secret=${{ secrets.GRADLE_TOKEN }} -PbuildNumber=${{ env.PATCH_VERSION }}
- name: Publish JAR to Space
run: ./gradlew :common:publish
env:
JB_SPACE_INTELLIJ_CLIENT_ID: ${{ secrets.MAVEN_SPACE_USERNAME }}
JB_SPACE_INTELLIJ_CLIENT_SECRET: ${{ secrets.MAVEN_SPACE_PASSWORD }}
github:
runs-on: ubuntu-latest
steps:
Expand Down
77 changes: 11 additions & 66 deletions build.gradle.kts
Original file line number Diff line number Diff line change
@@ -1,82 +1,27 @@
@file:Suppress("UnstableApiUsage")

import org.jetbrains.dokka.gradle.DokkaTask

fun properties(key: String) = providers.gradleProperty(key)
fun environment(key: String) = providers.environmentVariable(key)

plugins {
`kotlin-dsl`
`maven-publish`
alias(libs.plugins.pluginPublish)
alias(libs.plugins.dokka)
}

group = properties("projectGroup").get()
version = "${properties("majorVersion").get()}.${properties("buildNumber").get()}"
description = properties("description").get()

repositories {
mavenCentral()
}

dependencies {
testImplementation(gradleTestKit())
testImplementation(kotlin("test"))
testImplementation(kotlin("test-junit"))
}

kotlin {
jvmToolchain(11)
}

val dokkaHtml by tasks.getting(DokkaTask::class)

val javadocJar by tasks.registering(Jar::class) {
dependsOn(dokkaHtml)
archiveClassifier = "javadoc"
from(dokkaHtml.outputDirectory)
}

val sourcesJar = tasks.register<Jar>("sourcesJar") {
archiveClassifier = "sources"
from(sourceSets.main.get().allSource)
buildscript {
repositories {
gradlePluginPortal()
google()
mavenCentral()
}
}

artifacts {
archives(javadocJar)
archives(sourcesJar)
allprojects {
repositories {
google()
mavenCentral()
}
}

tasks {
test {
val testGradleHome = layout.buildDirectory.asFile.get().resolve("testGradleHome")

doFirst {
testGradleHome.mkdir()
}

systemProperties["test.gradle.home"] = testGradleHome
systemProperties["test.gradle.default"] = properties("gradleVersion").get()
systemProperties["test.gradle.version"] = properties("testGradleVersion").get()
systemProperties["test.gradle.arguments"] = properties("testGradleArguments").get()
outputs.dir(testGradleHome)
}

wrapper {
gradleVersion = properties("gradleVersion").get()
}
}

gradlePlugin {
website = properties("website")
vcsUrl = properties("vcsUrl")

plugins.create("qodana") {
id = properties("pluginId").get()
displayName = properties("name").get()
implementationClass = properties("pluginImplementationClass").get()
description = project.description
tags = properties("tags").map { it.split(',') }
}
}
45 changes: 45 additions & 0 deletions common/build.gradle.kts
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
fun properties(key: String) = providers.gradleProperty(key)
fun environment(key: String) = providers.environmentVariable(key)

plugins {
`maven-publish`
`kotlin-dsl`
`java-library`
}

val kotlinVersion by extra(libs.versions.kotlin.get())

group = "org.jetbrains.qodana.common"
version = "${properties("majorVersion").get()}.${properties("buildNumber").get()}"
kotlin {
jvmToolchain(11)
version = "2024.1.6"
}
publishing {
publications {
create<MavenPublication>("common") {
groupId = group.toString()
artifactId = "cli"
version = version.toString()
from(components["java"])
pom {
url.set("https://github.com/JetBrains/qodana-action")
licenses {
license {
name.set("Apache-2.0")
url.set("https://github.com/JetBrains/qodana-action/blob/main/LICENSE")
}
}
}
}
}
repositories {
maven {
url = uri("https://packages.jetbrains.team/maven/p/sa/maven-public")
credentials {
username = System.getenv("JB_SPACE_INTELLIJ_CLIENT_ID")
password = System.getenv("JB_SPACE_INTELLIJ_CLIENT_SECRET")
}
}
}
}
Original file line number Diff line number Diff line change
@@ -1,21 +1,30 @@
package org.jetbrains.qodana
package org.jetbrains.qodana.cli


import org.gradle.api.GradleException
import org.gradle.api.logging.Logger
import java.io.*
import java.io.File
import java.io.FileInputStream
import java.io.FileOutputStream
import java.io.IOException
import java.net.URL
import java.nio.channels.Channels
import java.nio.file.Files
import java.nio.file.attribute.PosixFilePermission

import java.security.MessageDigest
import java.util.logging.Logger

@Suppress("MemberVisibilityCanBePrivate")
class Installer {
val log: Logger = org.gradle.api.logging.Logging.getLogger(Installer::class.java)
val log: Logger = Logger.getLogger(Installer::class.java.name)
companion object {
private const val VERSION = "2024.1.6"
private const val RELEASE_DOWNLOAD_URL = "https://github.com/JetBrains/qodana-cli/releases/download/v%s/qodana_%s_%s"
private val CHECKSUMS = mapOf(
"windows_x86_64" to "cba8236cc8c650ecac61d543e744cb20e4763a26a075f37dc5909880de93b1f3",
"windows_arm64" to "b0547cd008959ca275d0a945e9ae025c4c9271cffa0e87ffaac883d164bf84e2",
"linux_x86_64" to "597d870f4c747d04d0280956306e2e7b9e003662d4600d93c1b69fcaffc2bb7b",
"linux_arm64" to "b127fc5fe46f5c197781ff0f30de4e4f68b3ba19c5748dcb87c3d1417a3d9f89",
"darwin_x86_64" to "847495bdeb8bffd2e13b0af8decdbd3b7b23735ad18746d0629e7a5e25c867de",
"darwin_arm64" to "e87ff91a64b8c77466938ee2020bf8636b46016ff9b587aa3fcaa356d6de6b72"
)

fun getQodanaUrl(platform: String = getPlatformName(), arch: String = getArchName(), version: String = VERSION): String {
return String.format(RELEASE_DOWNLOAD_URL, version, platform, arch) + getExtension()
Expand Down Expand Up @@ -43,23 +52,31 @@ class Installer {
else -> throw IllegalArgumentException("Unsupported OS: $systemName")
}
}

fun getChecksum(): String {
val platform = getPlatformName()
val arch = getArchName()
return CHECKSUMS["${platform}_${arch}"]
?: throw IllegalArgumentException("Unsupported combination of platform and architecture: ${platform}_${arch}")
}
}

fun setup(path: File, downloadURL: String = getQodanaUrl()): String {
if (path.exists()) {
return path.absolutePath
} else try {
download(downloadURL, path)
verifyChecksum(path, getChecksum())
} catch (e: IOException) {
throw GradleException("Unable to download latest qodana binary", e)
throw IOException("Unable to download latest qodana binary", e)
}

return path.absolutePath
}

private fun download(url: String, executablePath: File) {
executablePath.parentFile.mkdirs()
log.lifecycle("Downloading: {} to {}", url, executablePath)
log.info("Downloading: $url to $executablePath")
val website = URL(url)
Channels.newChannel(website.openStream()).use { rbc ->
FileOutputStream(executablePath).use { fos ->
Expand All @@ -73,7 +90,6 @@ class Installer {
if (getPlatformName() == "windows") {
return
}
log.debug("Setting file permissions")
val perms: MutableSet<PosixFilePermission> = HashSet()
perms.add(PosixFilePermission.OWNER_READ)
perms.add(PosixFilePermission.OWNER_WRITE)
Expand All @@ -82,4 +98,30 @@ class Installer {
perms.add(PosixFilePermission.OTHERS_EXECUTE)
Files.setPosixFilePermissions(file.toPath(), perms)
}
}

private fun verifyChecksum(file: File, expectedChecksum: String) {
val checksum = calculateChecksum(file)
if (checksum != expectedChecksum) {
throw IOException("Checksum verification failed. Expected: $expectedChecksum, but got: $checksum")
}
}

private fun calculateChecksum(file: File): String {
val digest = MessageDigest.getInstance("SHA-256")
FileInputStream(file).use { fis ->
val byteArray = ByteArray(1024)
var bytesCount: Int

while (fis.read(byteArray).also { bytesCount = it } != -1) {
digest.update(byteArray, 0, bytesCount)
}
}

val bytes = digest.digest()
val sb = StringBuilder()
for (byte in bytes) {
sb.append(String.format("%02x", byte))
}
return sb.toString()
}
}
29 changes: 29 additions & 0 deletions common/update-cli.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@ const { execSync } = require("child_process");
const path = require("path");
const cliJsonPath = "./cli.json";

const PLATFORMS = ["windows", "linux", "darwin"];
const ARCHS = ["x86_64", "arm64"];

function sha256sum(file) {
const hash = createHash("sha256");
hash.update(readFileSync(file));
Expand Down Expand Up @@ -113,6 +116,18 @@ function updateCircleCIChecksums(circleCIConfigPath) {
execSync("rm -rf qodana/ qodana_linux_x86_64.tar.gz");
}

function updateQodanaKtChecksums(checksums) {
const qodanaKtPath = "../src/main/kotlin/org/jetbrains/qodana/Qodana.kt";
let qodanaKtContent = fs.readFileSync(qodanaKtPath, "utf-8");

const newChecksums = `private val CHECKSUMS = mapOf(\n` +
checksums.map(({ platform, arch, checksum }) => ` "${platform}_${arch}" to "${checksum}"`).join(",\n") +
"\n )";

qodanaKtContent = qodanaKtContent.replace(/private val CHECKSUMS = mapOf\((.|\n)*?\)/, newChecksums);
fs.writeFileSync(qodanaKtPath, qodanaKtContent);
}

function updateVersions(latestVersion, currentVersion) {
const latestVersions = latestVersion.split(".");
const latestMajor = parseInt(latestVersions[0]);
Expand Down Expand Up @@ -161,6 +176,20 @@ async function main() {
updateVersions(latestVersion, currentVersion);
updateCliChecksums(latestVersion, "checksums.txt", cliJsonPath);
updateCircleCIChecksums("../orb/commands/scan.yml");
// Download binaries, calculate checksums, and update Qodana.kt
const checksums = [];
for (const platform of PLATFORMS) {
for (const arch of ARCHS) {
const url = `https://github.com/jetbrains/qodana-cli/releases/latest/download/qodana_${platform}_${arch}${platform === "windows" ? ".exe" : ""}`;
const filePath = path.join(__dirname, `qodana_${platform}_${arch}${platform === "windows" ? ".exe" : ""}`);
console.log(`Downloading ${url}...`);
await downloadFile(url, filePath);
const checksum = sha256sum(filePath);
checksums.push({ platform, arch, checksum });
fs.unlinkSync(filePath);
}
}
updateQodanaKtChecksums(checksums);
console.log("Versions updated successfully!");
} catch (error) {
console.error("An error occurred:", error);
Expand Down
2 changes: 2 additions & 0 deletions gradle/libs.versions.toml
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
[versions]
kotlin = "1.8.10"

# libraries
markdown = "0.5.0"
Expand All @@ -9,6 +10,7 @@ gradlePluginPublish = "1.2.1"
gradleChangelogPlugin = "2.2.0"

[libraries]
stdlib = { group = "org.jetbrains.kotlin" , name = "kotlin-stdlib", version.ref = "kotlin" }
markdown = { group = "org.jetbrains", name = "markdown", version.ref = "markdown" }

[plugins]
Expand Down
Loading
Loading