Are there any examples anyone can point me to of r...
# multiplatform
s
Are there any examples anyone can point me to of releasing a Kotlin multiplatform library to jcenter?
s
https://gitlab.com/serebit/strife is one of mine, it's common and JVM only at the moment.
s
Thanks for the link. Is this configured so that you can import each platform variant independently, or if you have a multiplatform project, you can import it once at the common level and it imports the rest?
Or is it both?
s
It's both, due to having
enableFeaturePreview("GRADLE_METADATA")
in
settings.gradle.kts
. You can declare each platform dependency (
strife-client-jvm
,
strife-client-metadata
) independently, or just add a dependency on
strife-client
in common and it applies the rest to the respective platforms
s
can you explain your implementation? I was about to copy the implementation from kotlinx.serialization - which is hundreds of lines long
yours seems really small and compact. I've only found 2 files that have reference to publishing
i.e. in the main gradle file applied to subprojects:
Copy code
afterEvaluate {
        tasks.withType<Jar> {
            // set jar base names to module paths, like strife-core and strife-samples-embeds
            archiveBaseName.set(fullPath)
        }
    }

    // will only run in subprojects with the maven-publish plugin already applied
    pluginManager.withPlugin("maven-publish") {
        publishing.configureBintray("serebit", "public", rootProject.name, System.getenv("BINTRAY_KEY"))

        afterEvaluate {
            publishing.publications.filterIsInstance<MavenPublication>().forEach {
                // replace project names in artifact with their module paths, ie core-jvm becomes strife-core-jvm
                it.artifactId = it.artifactId.replace(name, fullPath)
            }
        }
    }
Then in the client build.gradle, you are assigning the
maven-publish
plugin
What else are you doing?
s
The main thing is the call to
configureBintray
, which is a function in
buildSrc
that configures the Bintray repository. Everything else is done automatically via applying the plugin in subprojects due to the above call to
pluginManager.withPlugin
The official bintray plugin doesn't work very well with multiplatform, so I use the
maven-publish
plugin by itself
s
I was wondering where configure bintray was. Looking for it in buildSrc now
Copy code
fun PublishingExtension.configureBintray(
    userName: String,
    repositoryName: String,
    projectName: String,
    accessKey: String?
) = repositories.maven("<https://api.bintray.com/maven/serebit/$repositoryName/$projectName/;publish=0>") {
    name = "bintray"

    credentials {
        username = userName
        accessKey?.let { password = it }
    }
}
s
yeah, I see. This still seems like nothing.
s
That's actually all you need to configure the bintray repository
s
I've never used bintray / jcenter before.
do I need to have the repository already created on jcenter, or will it create it for me?
s
Copy code
val userName = "serebit"
val repositoryName = "public"
val projectName = "strife"

publishing.repositories.maven("<https://api.bintray.com/maven/$userName/$repositoryName/$projectName/;publish=0>") {
    name = "bintray"

    credentials {
        username = userName
        accessKey?.let { password = it }
    }
}
s
alright. thanks man. This seems super simple. Gonna give it a shot
s
You'll need to create the repository in Bintray first
along with the project
Create an account, then Add New Repository and name it something that makes sense. That's where all your projects will be grouped. Then create a project in that repository
s
by doing this, people will be able to access it in gradle via the
jcenter()
repo right?
s
When you call
publishAllPublicationsToBintrayRepository
, so long as your project exists at the URL you pass to the call to
maven
, it'll upload your artifacts to Bintray. Then you need to go to the Bintray website and click on the button that says "Publish artifacts"
Not yet. Once you have them added to your own project, then you need to request inclusion into jcenter for that project
s
cool beans. I really appreciate your help
s
No problem, I've had enough struggles with jcenter in the past and I'm happy to help anyone who runs into the same roadblocks 🙂
s
FYI - 1 repository should hold all my artifacts for multiple projects, right?
So naming it "maven" should make sense?
s
Yep.
I named mine
public
, but
maven
also works. So long as it's apparent what it's for
Also keep in mind that you need to have at least one version of a project published to your own repository before it can be included in jcenter, and your project's gradle group shouldn't just be something like
com.scott
, it should be
com.scott.project
if it's just
com.scott
, then you'll run into conflicts when adding other projects to jcenter, because group names in jcenter need to be unique
s
Did you apply
maven-publish
to your root gradle file so that you could resolve publishing and other things for the gradle for kotlin script gradle?
s
Yeah, if I didn't apply it to root then I wouldn't be able to resolve publishing. My code only checks subprojects for application of
maven-publish
If your project is single-module then you don't need to bother with that, just apply it in root and add the above
And your
password
under
credentials
should be your api key, which you can find in "edit profile" under (appropriately) API Key
s
hmmm, if I created the repository in an organization
I'm assuming userName would just be org
s
Yeah, it would
s
I think this is my last question before giving this a whirl. You call
publishing.configureBintray("serebit", "public", rootProject.name, System.getenv("BINTRAY_KEY"))
you only have one module that's uploaded from what I can tell, but if I have 2 modules (one is a mpp module called kotlin-html, and the other is a jvm module called kotlin-html-ktor)
your use of "projectName" I think maps to packageName in bintray. Would I need 2 packages for both of them?
or one package for both?
s
One package for both, so long as they're modules in the same project
s
So it's working for the multiplatform project
however, I noticed it's uploading weird because of
val fullPath = "${rootProject.name}${project.path.replace(":", "-")}"
s
Oh yeah, you don't need that
That's just because of how my modules are named
s
fixed that by removing the artifact id changing.
last thing I have to figure out is why my jvm project is uploading, but multiplatform isn't
s
What targets do you have declared
If it's only JVM and common, then what you see above is correct
s
errr
it's only jvm. not common
I'm assuming that the multiplatform plugin must have some sort of understanding of the multiplatform plugin, and is hooking a lot of stuff up for us? Otherwise this wouldn't work so easily I assume.
and the normal Kotlin plugin isn't doing any of that fancy stuff for me, which is why it's not working on my jvm only project?
s
It is, yes. The multiplatform plugin automatically creates publications for each target, including common and metadata, which is why we only need to declare the repository
You have to create the publications manually for the JVM plugin
s
ok. I should be able to find a tutorial for that. Should I just convert that module to use multiplatform, even if it's really only ever going to be JVM, as the ktor server it depends on is only JVM?
s
If you want to keep things simple for yourself, yeah. But if you really don't expect the module to ever be used in common code, then just do it manually
Maybe I should write a medium article on publishing multiplatform projects to bintray, just to save everyone else the headache 😆
s
Dude - you saved me a bunch of effort. I was 100% lost
no clue how you learned to do this
s
Lots of experience, and crawling through threads on here 😛
s
so after I publish this, how do I get it included in jcenter again?
s
There's a button on the project page named "Add to Jcenter". Click that, and submit the request. They should approve it within a couple days
s
Cool beans. Thanks again!
Any idea how to setup auto publish with multiplatform? That's a clear option on jvm variants
s
publish=1
k
i’m pretty sure all of the JB libraries are bintray. All of mine used to be but I moved over to maven central. That’s actually been pretty useful when publishing to windows. I think it would’ve been more difficult with the bintray process, but I digress. If you’re still having trouble with multiplatform and bintray there should be other samples to dig into
f
Made an article specifically for this
s
hmmm - got an email from them:
Copy code
We can see that under the groupID "dev/scottpierce/kotlin-html" there are four packages:

1.kotlin-html
2.kotlin-html-jvm
3.kotlin-html-ktor
4.kotlin-html-metadata

We can only approve one path for a single package.
For e.g "dev/scottpierce/kotlin-html/kotlin-html".

If the inclusion path you have requested to include is for a single package, it is missing one of the components. Otherwise, if the subpaths are for different packages, submit an inclusion for each.
Their terminology is weird. So I want one group id, but many artifacts inside that group id from a maven wagon perspective.
s
@spierce7 They asked me the same thing, and I gave a very confused answer. They ultimately went with com/serebit/strife
s
What do you mean?
Aren't they saying I'm missing something in order to release it under a single group?
s
What they're asking you is if you want all of the modules to be under the same path (group name) in jcenter
but they word it in a very odd way
s
Aren't they saying I'm missing something in order to release it under a single group?
s
s
But they don't specify what I'm missing
Oh
s
once I explained everything, they said it would go under the group name,
com/serebit/strife
so just explain that your project has multiple modules and that they should all go under the same group name, I guess
s
You got the exact same message.
I'll reply in a similar method. Thanks again!
s
No problem!
s
Why is uploading on the jvm so much more complicated then uploading on npm or the other package managers?
This seems dumb to me
Maven central was miserable to get setup
s
So I've heard, I've never actually used maven central
Jitpack exists if you want everything handled for you, but then you lose a lot of autonomy
k
maven central setup is not great, for sure, but once set up it’s easy to use. Bintray/jcenter isn’t that bad for jvm, but this whole metadata thing threw everything into the trash kind of. Last I heard, Jitpack didn’t work for MP.
I get the impression that bintray was trying to be the “not hard” option for the java world, but metadata made it also hard.
s
The metadata isn't actually an issue so long as you don't use the plugin that Bintray supplies. Klock doesn't publish with correct metadata (afaik), but Strife does
k
When I was using bintray, I was using the forked version from JB
s
I saw a thread where JB recommended using maven-publish rather than the vanilla Bintray plugin, or even the jetbrains forked one. Thus I started using maven-publish to configure the bintray repository, and I've had no problems since
k
I haven’t been following the gradle developments for bintray. I imagine 1.0 of metadata made that all more stable (or something)
s
Got a response:
Copy code
Hi spierce7,

Thank you for responding,

Please be informed that a valid path must contain a group ID and an artifact ID. For example, in the package path
“dev/scottpierce/kotlin-html/kotlin-html” the group ID is “dev/scottpierce/kotlin-html” and artefact ID is “ kotlin-html”. 
If you request to add a package just by the Group ID, the request will be approved and all the artifact IDs under that group ID will be added to JCenter. 

However, if you want to add more artifact IDs in the future with the same Group ID to the JCenter, you won’t be able to add it, as the Group ID already exists in JCenter. Please make sure that if you want to add a package in JCenter, provide us with a complete path (i.e. group ID+artifact ID). For multiple artifact IDs under the same group ID, please submit inclusion requests for each artifact ID.


Best regards,
Pranav Hegde
JFrog Support
s
pranav was the one who responded to me
it's important for him to note that the only project that you'll upload to bintray with that group id will be kotlin-html itself, and any artifacts are modules of that project
that's what i told him with strife and he accepted it
s
yeah. I responded with something similar I thought. I'm trying to figure out what an inclusion request is
s
The inclusion request is what you initially submitted by hitting "add to jcenter"
s
That doesn't really allow me to specify the group and artifact. I can only specify the snapshot group id.
s
I think he wants you to put it in the comment box
s
I'll wait to see how he responds I guess