ort
ort copied to clipboard
Make `spdx-utils` a multi-platform project
E.g. for user input validation in a front-end UI, it'd be valuable to parse and validate SPDX expressions directly in the front-end (typically JavaScript or TypeScript) code. While there is https://github.com/jslicense/spdx-expression-parse.js and related packages, they seem to not be well maintained, and are lacking several features / good error reporting as required by ORT-related projects.
So the idea is to turn ORT's own spdx-utils project into a Kotlin Multiplatform Project (KMP) and transpile it to JavaScript plus TypeScript declaration files. However, this requires to get rid of any JVM-only dependencies first.
The most "problematic" JVM dependency probably is ANTLR. A solution could be to use https://github.com/Strumenta/antlr-kotlin, but maybe only do a one-time conversion of the SPDX grammar (which has never been changed since its introduction) and commit the generated Kotlin files. Going forward, we'd manually maintain / adapt the generated code to our needs instead of dealing with ANTLR at all.
do a one-time conversion of the SPDX grammar
@mnonnenmacher, would that approach work for you?
Have you considered creating an entirely separate JS library?
Maybe it would increase the likelyhood of users of the library making contributions to it, and maybe gain more attraction for non-ort users.
Have you considered creating an entirely separate JS library?
Yes. We at Double Open are in parallel also looking into creating a separate library.
However, I believe there's value in having the exact same logic in both JVM and JS libraries, without rewriting the code for that. And on top of that, it's a great KMP experiment.
However, I believe there's value in having the exact same logic in both JVM and JS libraries, without rewriting the code for that. And on top of that, it's a great KMP experiment.
Maybe we could go even on step further with the experiment and publish the JS build as an NPM package once everything is working.
do a one-time conversion of the SPDX grammar
@mnonnenmacher, would that approach work for you?
Yes, that would be fine with me.
publish the JS build as an NPM package
Sure, that would be the plan.
do a one-time conversion of the SPDX grammar
@mnonnenmacher, would that approach work for you?
Yes, that would be fine with me.
Unfortunately, looks like this would not work as expected, as I just learned that the generated Kotlin code is not self-contained, but depends on an ANTLR-specific runtime.
Unfortunately, looks like this would not work as expected, as I just learned that https://github.com/antlr/antlr5/issues/1#issuecomment-1913587512, but depends on an ANTLR-specific runtime.
I am not sure if this is helpful but please note that that runtime can be compiled down to JS, and Typescript type definitions can be generated for that too, so it can be used in a JS application. Would it be useful if such runtime was packaged as an NPM package?
Would it be useful if such runtime was packaged as an NPM package?
I guess it would, yes.
There is no need to build the runtime into an npm package.
What you need to do is depend on the runtime at the common level, and @JsExport the entry points you want to use from JS or TS.
E.g. for user input validation in a front-end UI, it'd be valuable to parse and validate SPDX expressions directly in the front-end
Export a validation function from a front-end module:
@JsExport
public fun validate(content: String): Boolean {
val parser = YourCustomAntlrParser(...)
val root = parser.whatever()
...
}
And use it from JavaScript:
import validate = your.ort.exported.namespace.validate;
const isValid = validate("your-content");
JS-exporting the entire runtime is problematic, and currently impossible.
As the SPDX expression grammar is so simple I have started work on a hand-written parser and am already mostly done. That should make it much easier to make this a true multiplatform module also for other targets like native or WASM. Apart from the SPDX expression parser there is also the SPDX document model which currently depends on Jackson. That could be changed to kotlinx.serialization but I don't know if this introduces new challenges when we want to publish the module as an NPM library. In that context it could make sense to split the module into two separate modules, also because there are proabably a lot more use cases for parsing SPDX expressions than for parsing whole SPDX documents.
In that context it could make sense to split the module into two separate modules
I agree. Porting our SPDX document support to kotlinx.serialization could make sense nonetheless.