Kotlin 在Ktor应用程序模块中获取命令行参数,而不是Main?

Kotlin 在Ktor应用程序模块中获取命令行参数,而不是Main?,kotlin,ktor,Kotlin,Ktor,我试图从Ktor构建一个应用程序,最终应该通过fatjar执行。 fatjar允许使用如下参数: java-jar myApp.jar XXXXX yyyy 我知道如何在主模块中获取XXXXX(通过使用简单的args[0]),但在应用程序模块中获取该值时遇到困难 我想这样做: fun main(args: Array<String>) { val port = System.getenv("PORT")?.toInt() ?: 8080 val s

我试图从Ktor构建一个应用程序,最终应该通过fatjar执行。 fatjar允许使用如下参数:

java-jar myApp.jar XXXXX yyyy

我知道如何在主模块中获取
XXXXX
(通过使用简单的
args[0]
),但在应用程序模块中获取该值时遇到困难

我想这样做:

fun main(args: Array<String>) {
    val port = System.getenv("PORT")?.toInt() ?: 8080
    val status = args[0]
    embeddedServer(Netty, port = port, module = (Application::mainModule())).start(wait = true)
}

fun Application.mainModule() {
    routing {
        get("/status") {
            call.respondText(
                <status variable from main function>,
                contentType = ContentType.Text.Html
            )
        }
    }
}
fun main(args:Array){
val port=System.getenv(“端口”)?.toInt():8080
val状态=参数[0]
embeddedServer(Netty,port=port,module=(Application::mainModule())。启动(wait=true)
}
有趣的应用程序。main模块(){
路由{
获取(“/状态”){
call.respondText(
,
contentType=contentType.Text.Html
)
}
}
}

您可以用普通lambda替换
模块
参数的方法参考。 在此lambda中,使用所需参数调用模块函数:

fun Application.mainModule(args: Array<String>) {
    routing {
        get("/status") {
            //...
        }
    }
}

fun main(args: Array<String>) {
    val server = embeddedServer(Netty, port = 8080) {
        mainModule(args)
    }
    server.start(wait = true)
}
这就是您可以提供
Application::mainModule
a作为函数参考的原因。它与参数的类型定义完全匹配。但您也可以提供一个尾随lambda,而不是此函数引用:

val server = embeddedServer(Netty, port = 8080) { 
    // this is Application
    routing {
        get("/status") {
            //...
        }
    }
}

在此lambda
中,此
属于
应用程序
类型,与函数
应用程序.main模块
中的类型完全相同。这意味着在这个lambda中,您可以轻松地调用
Application
类型的其他函数。在我的回答中,我创建了
应用程序.mainModule
,其中
参数为args
,并在后面的lambda中调用此函数。

要传递新的配置参数,可以在其前面加上
-p:propName=

因此,如果要通过命令行传递名为
csv
的属性值,可以执行以下操作:

fun main(args:Array){
val csvFileName=“-P:csv=${args[0]}”
EngineMain.main(arrayOf(csvFileName))
}
您还可以通过将
-p:csv=myfile.csv
用作命令行参数来传递参数,而无需修改
args

然后,在您的模块中,您可以通过
environment.config.property(“csv”).getString()
访问它

fun Application.module(){
val csvFileName=environment.config.property(“csv”).getString()
println(csvFileName)
}

您可以在中阅读有关配置Ktor应用程序的更多信息。

这非常有效!!!谢谢你,雷内。我现在很难理解这到底是怎么回事。。。如果你能给我一些指导,让我知道为什么lambda会在这里提供帮助,那就太棒了。但那已经很棒了!非常感谢。在保留io.ktor.server.netty.EngineMain.main(args)的功能的同时,还有什么方法可以做到这一点吗?@daka请检查我的答案,它应该会有帮助。谢谢,我今天晚些时候会尝试:)这对我来说非常有效。非常感谢。谢谢,你觉得你能回答这个问题吗?
val server = embeddedServer(Netty, port = 8080) { 
    // this is Application
    routing {
        get("/status") {
            //...
        }
    }
}