วิธีส่งตัวเลือก JVM จาก bootRun


100

ฉันกำลังพัฒนาแอปพลิเคชันเว็บ Spring แบบง่ายที่สื่อสารกับโฮสต์ระยะไกลและฉันต้องการทดสอบในเครื่องหลังพร็อกซีขององค์กร ฉันใช้ปลั๊กอิน gradle "Spring Boot" และคำถามคือฉันจะระบุการตั้งค่าพร็อกซีสำหรับ JVM ได้อย่างไร

ฉันได้ลองทำหลายวิธี:

  1. gradle -Dhttp.proxyHost=X.X.X.X -Dhttp.proxyPort=8080 bootRun
  2. export JAVA_OPTS="-Dhttp.proxyHost=X.X.X.X -Dhttp.proxyPort=8080"
  3. export GRADLE_OPTS="-Dhttp.proxyHost=X.X.X.X -Dhttp.proxyPort=8080"

แต่ดูเหมือนว่าจะไม่มีการทำงานใด ๆ - "NoRouteToHostException" พ่นรหัส "เครือข่าย" นอกจากนี้ฉันได้เพิ่มโค้ดพิเศษเพื่อแก้จุดบกพร่อง JVM start อาร์กิวเมนต์

    RuntimeMXBean runtimeMxBean = ManagementFactory.getRuntimeMXBean();
    List<String> arguments = runtimeMxBean.getInputArguments();
    for (String arg: arguments) System.out.println(arg);

และพิมพ์อาร์กิวเมนต์เดียวเท่านั้น: "-Dfile.encoding = UTF-8"

หากฉันตั้งค่าคุณสมบัติของระบบในรหัส:

    System.setProperty("http.proxyHost", "X.X.X.X");
    System.setProperty("http.proxyPort", "8080");

ทุกอย่างทำงานได้ดี!

คำตอบ:


109

คำตอบเดิม (โดยใช้ Gradle 1.12 และ Spring Boot 1.0.x):

bootRunงานของปลั๊กอิน gradle ฤดูใบไม้ผลิ Boot ขยายงาน JavaExec gradle ดูนี้

นั่นหมายความว่าคุณสามารถกำหนดค่าปลั๊กอินเพื่อใช้พร็อกซีได้โดยเพิ่ม:

bootRun {
   jvmArgs = "-Dhttp.proxyHost=xxxxxx", "-Dhttp.proxyPort=xxxxxx"
}

ไปยังไฟล์บิลด์ของคุณ

แน่นอนคุณสามารถใช้systemPropertiesแทนjvmArgs

หากคุณต้องการเพิ่ม jvmArgs ตามเงื่อนไขจากบรรทัดคำสั่งคุณสามารถทำสิ่งต่อไปนี้:

bootRun {
    if ( project.hasProperty('jvmArgs') ) {
        jvmArgs project.jvmArgs.split('\\s+')
    }
}

gradle bootRun -PjvmArgs="-Dwhatever1=value1 -Dwhatever2=value2"

คำตอบที่อัปเดต:

หลังจากลองใช้วิธีแก้ปัญหาของฉันข้างต้นโดยใช้Spring Boot 1.2.6.RELEASEและGradle 2.7ฉันสังเกตว่ามันไม่ทำงานตามที่ความคิดเห็นบางส่วนกล่าวถึง อย่างไรก็ตามสามารถทำการปรับแต่งเล็กน้อยเพื่อกู้คืนสถานะการทำงาน

รหัสใหม่คือ:

bootRun {
   jvmArgs = ["-Dhttp.proxyHost=xxxxxx", "-Dhttp.proxyPort=xxxxxx"]
}

สำหรับอาร์กิวเมนต์แบบฮาร์ดโค้ดและ

bootRun {
    if ( project.hasProperty('jvmArgs') ) {
        jvmArgs = (project.jvmArgs.split("\\s+") as List)

    }
}

สำหรับอาร์กิวเมนต์ที่ให้มาจากบรรทัดคำสั่ง


4
ฉันไม่ต้องการให้ตัวเลือกนี้ "ฮาร์ดโค้ด" ในไฟล์บิวด์ จะเป็นการดีที่จะระบุการตั้งค่าพร็อกซีได้ เช่น - ใช้อาร์กิวเมนต์บรรทัดคำสั่ง
Evgeny

ไม่ทำงาน: "> ไม่พบคุณสมบัติ" args "ใน root project"
Evgeny

คุณคัดลอกรหัสถูกต้องหรือไม่ ฉันได้ทำการอัปเดต ไม่มีargsทรัพย์สิน.
geoand

7
ฉันลองวันนี้และวิธีเดียวที่ได้ผลคือการลบรายการสตริงด้วยวงเล็บเหลี่ยมเช่น bootRun {jvmArgs = ["-Dhttp.proxyHost = xxxxxx", "-Dhttp.proxyPort = xxxxxx"]}
Valentino Dell ' Aica

คุณใช้ gradle รุ่นใด
geoand

73
bootRun {
  // support passing -Dsystem.property=value to bootRun task
  systemProperties = System.properties
}

นี้ควรจะผ่านตัวเลือก JVM bootRunทั้งหมดเพื่อให้แอปเริ่มต้นผ่าน


2
นี่เป็นวิธีที่ดีที่สุดในการส่งผ่านตัวเลือกบรรทัดคำสั่งไปยัง JVM
anubhava

@Marvin Frommhold ขอบคุณสำหรับคำตอบของคุณ แนวทางตรงไปตรงมาอย่างไม่น่าเชื่อ สำหรับ noobs อย่างฉันมันจะมีประโยชน์ถ้าคุณเพิ่มรายละเอียดอีกเล็กน้อย ข้อเสนอแนะ: (1) แสดงการเรียกบรรทัดคำสั่ง gradle พร้อมอาร์กิวเมนต์; (2) แสดงวิธีอ้างอิงอาร์กิวเมนต์ใน Spring Boot เช่น @Value ("$ {property: default}"); (3) ภาพหน้าจอของกล่องโต้ตอบ IntelliJ ที่ส่งผ่านพารามิเตอร์ก็จะเป็นประโยชน์เช่นกัน
Brett

1
น่าเศร้าสำหรับฉันการเพิ่มสิ่งนี้ทำให้ gradle bootRun ล้มเหลวอย่างน่าสยดสยองด้วย "org.apache.catalina.LifecycleException: คอนเทนเนอร์ลูกล้มเหลวระหว่างการเริ่มต้น" แม้ว่าจะไม่ผ่าน
พารามิเตอร์

แก้ไขโดยการเลือกเชอร์รี่คุณสมบัติที่ฉันต้องการเช่นเดียวกับคำตอบของstackoverflow.com/questions/23689054
tkruse

7

ใน gradle build script กำหนด systemProperties สำหรับรันงาน

//to provide the properties while running the application using spring-boot's run task
    run {
        systemProperties['property name'] = 'value'
    }

และgradle runควรยอมรับค่านี้

หรือกำหนดคุณสมบัติระดับโปรเจ็กต์ตามที่กล่าวไว้ใน http://forums.gradle.org/gradle/topics/how_can_i_provide_command_line_args_to_application_started_with_gradle_run


1
ใช่วิธีนี้ใช้ได้ผล แต่ฉันไม่ต้องการให้รหัสนี้อยู่ภายใต้การควบคุมแหล่งที่มา ฉันเชื่อว่าวิธีแก้ปัญหาที่ "ถูกต้องที่สุด" คือการส่งผ่านตัวเลือกนี้โดยตรงในบรรทัดคำสั่ง มันเป็นวิธีใด?
Evgeny

1
ลิงก์ที่กล่าวถึงในโพสต์มีวิธีส่งผ่านจากบรรทัดคำสั่ง
suman j

5

@marvin ขอบคุณสำหรับโพสต์ของคุณมันมีประโยชน์มาก

แบ่งปันวิธีที่ฉันใช้:

test {
  // support passing -Dsystem.property=value to bootRun task
  systemProperties = System.properties
}

ฉันมีการทดสอบ JUnit ที่ฉันต้องการข้ามเว้นแต่จะมีการใช้คุณสมบัติเพื่อรวมการทดสอบดังกล่าว การใช้ JUnit Assume เพื่อรวมการทดสอบตามเงื่อนไข:

//first line of test
assumeThat(Boolean.parseBoolean(System.getProperty("deep.test.run","false"),true)

การทำเช่นนี้กับ gradle จำเป็นต้องให้คุณสมบัติของระบบที่จัดเตรียมไว้ในขณะที่รัน gradle build แสดงไว้ที่นี่

gradle build -Ddeep.test.run=true

ผ่านการทดสอบอย่างแท้จริง

หวังว่านี่จะช่วยให้ผู้อื่นลองใช้แนวทางนี้ในการทดสอบตามเงื่อนไข


3
bootRun {
  args = ['myProgramArgument1', 'myProgramArgument2']
}

การใช้ jvmArgs อาจทำให้เกิดปัญหาการเริ่มต้น JVM การใช้ args ช่วยให้คุณส่งผ่านอาร์กิวเมนต์โปรแกรมที่คุณกำหนดเองได้


คุณสามารถแสดงวิธีใช้อาร์กิวเมนต์เหล่านี้ใน Application.class หรือใน Bootstrap.class ได้อย่างไร (ฉันใช้ grails 3.xx)
Stefano Scarpanti


1

ฉันประสบปัญหาที่คล้ายกัน bootRun ต้องการพารามิเตอร์บางอย่าง แต่ฉันไม่รู้สึกอยากแก้ไข bootRun เพราะฉันต้องการรักษาความยืดหยุ่นและยึดติดกับพฤติกรรม bootRun มาตรฐาน คำแนะนำของฉันคือเพิ่มงานที่กำหนดเอง (สมมติว่า bootRunDev, bootRunProxy) ที่ขยาย bootRun ตามที่อธิบายไว้ในข้อมูลโค้ดต่อไปนี้

task bootRunPxy(type: org.springframework.boot.gradle.run.BootRunTask, dependsOn: 'build') {
    group = 'Application'
    doFirst() {
        main = project.mainClassName
        classpath = sourceSets.main.runtimeClasspath
        systemProperty 'http.proxyHost', 'xxxxx'
        systemProperty 'http.proxyPort', 'yyyyy'
    }
}

ฉันไม่มีสภาพแวดล้อมในการใช้สคริปต์ แต่ฉันใช้วิธีนี้เพื่อส่งผ่านโปรไฟล์ไปยังสปริงโดยใช้คุณสมบัติ spring.profiles.active เครดิตควรไปที่Karol Kaliński

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.