build.gradle.kts 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286
  1. @file:Suppress("UnstableApiUsage", "UNUSED_VARIABLE")
  2. import org.jetbrains.dokka.gradle.DokkaTask
  3. import java.time.Duration
  4. import kotlin.math.pow
  5. buildscript {
  6. repositories {
  7. mavenLocal()
  8. // maven(url = "https://mirrors.huaweicloud.com/repository/maven")
  9. maven(url = "https://dl.bintray.com/kotlin/kotlin-eap")
  10. jcenter()
  11. google()
  12. }
  13. dependencies {
  14. classpath("com.github.jengelman.gradle.plugins:shadow:5.2.0")
  15. classpath("com.android.tools.build:gradle:${Versions.Android.androidGradlePlugin}")
  16. classpath("org.jetbrains.kotlin:kotlin-gradle-plugin:${Versions.Kotlin.stdlib}")
  17. classpath("org.jetbrains.kotlin:kotlin-serialization:${Versions.Kotlin.stdlib}")
  18. classpath("org.jetbrains.kotlinx:atomicfu-gradle-plugin:${Versions.Kotlin.atomicFU}")
  19. classpath("org.jetbrains.kotlinx:binary-compatibility-validator:${Versions.Kotlin.binaryValidator}")
  20. }
  21. }
  22. plugins {
  23. id("org.jetbrains.dokka") version Versions.Kotlin.dokka apply false
  24. // id("com.jfrog.bintray") version Versions.Publishing.bintray apply false
  25. }
  26. // https://github.com/kotlin/binary-compatibility-validator
  27. //apply(plugin = "binary-compatibility-validator")
  28. project.ext.set("isAndroidSDKAvailable", false)
  29. // until
  30. // https://youtrack.jetbrains.com/issue/KT-37152,
  31. // are fixed.
  32. /*
  33. runCatching {
  34. val keyProps = Properties().apply {
  35. file("local.properties").takeIf { it.exists() }?.inputStream()?.use { load(it) }
  36. }
  37. if (keyProps.getProperty("sdk.dir", "").isNotEmpty()) {
  38. project.ext.set("isAndroidSDKAvailable", true)
  39. } else {
  40. project.ext.set("isAndroidSDKAvailable", false)
  41. }
  42. }.exceptionOrNull()?.run {
  43. project.ext.set("isAndroidSDKAvailable", false)
  44. }*/
  45. allprojects {
  46. group = "net.mamoe"
  47. version = Versions.Mirai.version
  48. repositories {
  49. mavenLocal()
  50. // maven(url = "https://mirrors.huaweicloud.com/repository/maven")
  51. maven(url = "https://dl.bintray.com/kotlin/kotlin-eap")
  52. jcenter()
  53. google()
  54. }
  55. }
  56. subprojects {
  57. afterEvaluate {
  58. apply(plugin = "com.github.johnrengelman.shadow")
  59. val kotlin =
  60. runCatching {
  61. (this as ExtensionAware).extensions.getByName("kotlin") as? org.jetbrains.kotlin.gradle.dsl.KotlinMultiplatformExtension
  62. }.getOrNull() ?: return@afterEvaluate
  63. val shadowJvmJar by tasks.creating(com.github.jengelman.gradle.plugins.shadow.tasks.ShadowJar::class) {
  64. group = "mirai"
  65. val compilations =
  66. kotlin.targets.filter { it.platformType == org.jetbrains.kotlin.gradle.plugin.KotlinPlatformType.jvm }
  67. .map { it.compilations["main"] }
  68. compilations.forEach {
  69. dependsOn(it.compileKotlinTask)
  70. }
  71. compilations.forEach {
  72. from(it.output)
  73. }
  74. configurations = compilations.map { it.compileDependencyFiles as Configuration }
  75. this.exclude { file ->
  76. file.name.endsWith(".sf", ignoreCase = true)
  77. .also { if (it) println("excluded ${file.name}") }
  78. }
  79. this.manifest {
  80. this.attributes(
  81. "Manifest-Version" to 1,
  82. "Implementation-Vendor" to "Mamoe Technologies",
  83. "Implementation-Title" to [email protected](),
  84. "Implementation-Version" to [email protected]()
  85. )
  86. }
  87. }
  88. val githubUpload by tasks.creating {
  89. group = "mirai"
  90. dependsOn(shadowJvmJar)
  91. doFirst {
  92. timeout.set(Duration.ofHours(3))
  93. findLatestFile().let { (_, file) ->
  94. val filename = file.name
  95. println("Uploading file $filename")
  96. runCatching {
  97. upload.GitHub.upload(
  98. file,
  99. project,
  100. "mirai-repo",
  101. "shadow/${project.name}/$filename"
  102. )
  103. }.exceptionOrNull()?.let {
  104. System.err.println("GitHub Upload failed")
  105. it.printStackTrace() // force show stacktrace
  106. throw it
  107. }
  108. }
  109. }
  110. }
  111. apply(plugin = "org.jetbrains.dokka")
  112. this.tasks {
  113. val dokka by getting(DokkaTask::class) {
  114. outputFormat = "html"
  115. outputDirectory = "$buildDir/dokka"
  116. }
  117. val dokkaMarkdown by creating(DokkaTask::class) {
  118. outputFormat = "markdown"
  119. outputDirectory = "$buildDir/dokka-markdown"
  120. }
  121. val dokkaGfm by creating(DokkaTask::class) {
  122. outputFormat = "gfm"
  123. outputDirectory = "$buildDir/dokka-gfm"
  124. }
  125. }
  126. val dokkaGitHubUpload by tasks.creating {
  127. group = "mirai"
  128. val dokkaTaskName = "dokka"
  129. dependsOn(tasks.getByName(dokkaTaskName))
  130. doFirst {
  131. val baseDir = file("./build/$dokkaTaskName/${project.name}")
  132. timeout.set(Duration.ofHours(6))
  133. file("build/$dokkaTaskName/").walk()
  134. .filter { it.isFile }
  135. .map { old ->
  136. if (old.name == "index.md") File(old.parentFile, "README.md").also { new -> old.renameTo(new) }
  137. else old
  138. }
  139. // optimize md
  140. .forEach { file ->
  141. if (file.endsWith(".md")) {
  142. file.writeText(
  143. file.readText().replace("index.md", "README.md", ignoreCase = true)
  144. .replace(Regex("""```\n([\s\S]*?)```""")) {
  145. "\n" + """
  146. ```kotlin
  147. $it
  148. ```
  149. """.trimIndent()
  150. })
  151. } /* else if (file.name == "README.md") {
  152. file.writeText(file.readText().replace(Regex("""(\n\n\|\s)""")) {
  153. "\n\n" + """"
  154. |||
  155. |:----------------------------------------------------------------------------------------|:---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
  156. |
  157. """.trimIndent()
  158. })
  159. }*/
  160. val filename = file.toRelativeString(baseDir)
  161. println("Uploading file $filename")
  162. runCatching {
  163. upload.GitHub.upload(
  164. file,
  165. project,
  166. "mirai-doc",
  167. "${project.name}/${project.version}/$filename"
  168. )
  169. }.exceptionOrNull()?.let {
  170. System.err.println("GitHub Upload failed")
  171. it.printStackTrace() // force show stacktrace
  172. throw it
  173. }
  174. }
  175. }
  176. }
  177. val cuiCloudUpload by tasks.creating {
  178. group = "mirai"
  179. dependsOn(shadowJvmJar)
  180. doFirst {
  181. timeout.set(Duration.ofHours(3))
  182. findLatestFile().let { (_, file) ->
  183. val filename = file.name
  184. println("Uploading file $filename")
  185. runCatching {
  186. upload.CuiCloud.upload(
  187. file,
  188. project
  189. )
  190. }.exceptionOrNull()?.let {
  191. System.err.println("CuiCloud Upload failed")
  192. it.printStackTrace() // force show stacktrace
  193. throw it
  194. }
  195. }
  196. }
  197. }
  198. }
  199. afterEvaluate {
  200. tasks.filterIsInstance<DokkaTask>().forEach { task ->
  201. with(task) {
  202. configuration {
  203. perPackageOption {
  204. prefix = "net.mamoe.mirai"
  205. skipDeprecated = true
  206. }
  207. perPackageOption {
  208. prefix = "net.mamoe.mirai.internal"
  209. suppress = true
  210. }
  211. perPackageOption {
  212. prefix = "net.mamoe.mirai.event.internal"
  213. suppress = true
  214. }
  215. perPackageOption {
  216. prefix = "net.mamoe.mirai.utils.internal"
  217. suppress = true
  218. }
  219. perPackageOption {
  220. prefix = "net.mamoe.mirai.qqandroid.utils"
  221. suppress = true
  222. }
  223. perPackageOption {
  224. prefix = "net.mamoe.mirai.qqandroid.contact"
  225. suppress = true
  226. }
  227. perPackageOption {
  228. prefix = "net.mamoe.mirai.qqandroid.message"
  229. suppress = true
  230. }
  231. perPackageOption {
  232. prefix = "net.mamoe.mirai.qqandroid.network"
  233. suppress = true
  234. }
  235. }
  236. }
  237. }
  238. }
  239. }
  240. fun Project.findLatestFile(): Map.Entry<String, File> {
  241. return File(projectDir, "build/libs").walk()
  242. .filter { it.isFile }
  243. .onEach { println("all files=$it") }
  244. .filter { it.name.matches(Regex("""${project.name}-[0-9][0-9]*(\.[0-9]*)*.*\.jar""")) }
  245. .onEach { println("matched file: ${it.name}") }
  246. .associateBy { it.nameWithoutExtension.substringAfterLast('-') }
  247. .onEach { println("versions: $it") }
  248. .maxBy { (version, _) ->
  249. version.split('.').let {
  250. if (it.size == 2) it + "0"
  251. else it
  252. }.reversed().foldIndexed(0) { index: Int, acc: Int, s: String ->
  253. acc + 100.0.pow(index).toInt() * (s.toIntOrNull() ?: 0)
  254. }
  255. } ?: error("cannot find any file to upload")
  256. }