java.io.Console รองรับใน Eclipse IDE


103

ฉันใช้ Eclipse IDE เพื่อพัฒนารวบรวมและรันโปรเจ็กต์ Java ของฉัน วันนี้ฉันพยายามใช้java.io.Consoleคลาสเพื่อจัดการเอาต์พุตและที่สำคัญกว่านั้นคืออินพุตของผู้ใช้

ปัญหาคือจะSystem.console()ส่งกลับnullเมื่อแอปพลิเคชันทำงาน "ถึง" Eclipse Eclipse รันโปรแกรมบนกระบวนการเบื้องหลังแทนที่จะเป็นกระบวนการระดับบนสุดด้วยหน้าต่างคอนโซลที่เราคุ้นเคย

มีวิธีบังคับให้ Eclipse รันโปรแกรมเป็นกระบวนการระดับบนสุดหรืออย่างน้อยก็สร้าง Console ที่ JVM จะรับรู้? มิฉะนั้นฉันถูกบังคับให้ jar โปรเจ็กต์และรันบนสภาพแวดล้อมบรรทัดคำสั่งภายนอกไปยัง Eclipse


ยังเห็นstackoverflow.com/questions/26470972/...ฉันระบุSystem.outและSystem.inจะเพียงพอสำหรับกรณีการใช้งานของฉันและ abondaned System.console()ใช้
OneWorld

ฉันส่งออกโปรเจ็กต์เป็น jar ที่
รันได้

คำตอบ:


50

ฉันคิดว่าคุณต้องการใช้การดีบักทีละขั้นตอนจาก Eclipse คุณสามารถเรียกใช้คลาสภายนอกได้โดยการตั้งค่าคลาสที่สร้างขึ้นในไดเร็กทอรี bin บนพา ธ คลาส JRE

java -cp workspace\p1\bin;workspace\p2\bin foo.Main

คุณสามารถดีบักโดยใช้ตัวดีบักระยะไกลและใช้ประโยชน์จากไฟล์คลาสที่สร้างขึ้นในโครงการของคุณ

ในตัวอย่างนี้โครงสร้างโครงการ Eclipse มีลักษณะดังนี้:

workspace\project\
                 \.classpath
                 \.project
                 \debug.bat
                 \bin\Main.class
                 \src\Main.java

1. เริ่มคอนโซล JVM ในโหมดดีบัก

debug.batเป็นไฟล์แบตช์ของ Windows ที่ควรเรียกใช้ภายนอกจากคอนโซลcmd.exe

@ECHO OFF
SET A_PORT=8787
SET A_DBG=-Xdebug -Xnoagent -Xrunjdwp:transport=dt_socket,address=%A_PORT%,server=y,suspend=y
java.exe %A_DBG% -cp .\bin Main

ในข้อโต้แย้งพอร์ตการแก้ปัญหาที่ได้รับการตั้งค่าให้8787 ระงับ y =อาร์กิวเมนต์บอก JVM จะรอจนกว่าจะยึดติดดีบัก

2. สร้างการกำหนดค่าการเปิดตัวการแก้ปัญหา

ใน Eclipse เปิดไดอะล็อก Debug (Run> Open Debug Dialog ... ) และสร้างคอนฟิกูเรชันRemote Java Applicationใหม่ด้วยการตั้งค่าต่อไปนี้:

  • โครงการ:ชื่อโครงการของคุณ
  • ประเภทการเชื่อมต่อ: Standard (Socket Attach)
  • โฮสต์: localhost
  • พอร์ต: 8787

3. การแก้จุดบกพร่อง

ดังนั้นสิ่งที่คุณต้องทำทุกครั้งที่คุณต้องการแก้ไขข้อบกพร่องของแอปคือ:

  • กำหนดจุดพัก
  • เปิดไฟล์แบตช์ในคอนโซล
  • เปิดการกำหนดค่าการดีบัก

คุณสามารถติดตามปัญหานี้ในข้อผิดพลาด 122429 คุณสามารถทำงานรอบปัญหานี้ในแอพลิเคชันของคุณโดยใช้ชั้น abstraction ตามที่อธิบายไว้ที่นี่


1
ฉันจะใส่pauseท้ายไฟล์แบตช์นั้นด้วยเพื่อให้คุณเห็นข้อความแสดงข้อผิดพลาดที่กะพริบก่อนที่จะปิด
Matt Lyons

10
นี่คือฟางเส้นสุดท้ายสำหรับฉัน ถ้าฉันต้องทำทั้งหมดนี้เพื่อแก้จุดบกพร่องฉันกำลังเปลี่ยนกลับไปใช้ Netbeans ข้อบกพร่องที่ไม่ได้รับการแก้ไขและการรบกวน UI จำนวนมากใน Eclipse มันไม่ตลกเลย
nuzzolilo

@Nuzzolilo นี่เป็นเพียงการดีบักระยะไกล คุณสามารถดีบักแบบโลคัลใน eclipse โดยไม่ต้องทำทั้งหมด
Laplie Anderson

35

วิธีแก้ปัญหาที่ฉันใช้คือใช้ System.in/System.out แทน Console เมื่อใช้ Eclipse ตัวอย่างเช่นแทนที่จะเป็น:

String line = System.console().readLine();

คุณสามารถใช้ได้:

BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(System.in));
String line = bufferedReader.readLine();

20
ฉันไม่คิดว่าคุณจะสามารถอ่านรหัสผ่านโดยมีการปิดบังรหัสผ่านด้วยวิธีนั้น
Sualeh Fatehi

3
... และความจำเป็นที่จะจับหนึ่งซึ่งไม่ได้โยนในกรณีของIOException Console.readLine()
dma_k

5

สาเหตุนี้เกิดขึ้นเนื่องจาก eclipse เรียกใช้แอปของคุณเป็นกระบวนการพื้นหลังและไม่ใช่กระบวนการระดับบนสุดด้วยคอนโซลระบบ


5

คุณสามารถใช้คลาสได้ด้วยตัวเอง ต่อไปนี้เป็นตัวอย่าง:

public class Console {
    BufferedReader br;
    PrintStream ps;

    public Console(){
        br = new BufferedReader(new InputStreamReader(System.in));
        ps = System.out;
    }

    public String readLine(String out){
        ps.format(out);
        try{
            return br.readLine();
        }catch(IOException e)
        {
            return null;
        }
    }
    public PrintStream format(String format, Object...objects){
        return ps.format(format, objects);
    }
}

4

พบบางอย่างเกี่ยวกับเรื่องนี้ได้ที่http://www.stupidjavatricks.com/?p=43 http://www.stupidjavatricks.com/?p=43

และน่าเศร้าเนื่องจากคอนโซลเป็นที่สิ้นสุดคุณจึงไม่สามารถขยายเพื่อสร้าง aa wrapper รอบ ๆ system.in และ system.out ได้เช่นกัน แม้แต่ในคอนโซล eclipse คุณก็ยังเข้าถึงสิ่งเหล่านั้นได้ นั่นอาจเป็นสาเหตุที่ eclipse ยังไม่เสียบสิ่งนี้เข้ากับคอนโซลของพวกเขา ...

ฉันเข้าใจว่าทำไมคุณไม่ต้องการมีวิธีอื่นในการรับคอนโซลอื่นนอกจาก System.console โดยไม่มีตัวตั้งค่า แต่ฉันไม่เข้าใจว่าทำไมคุณไม่ต้องการให้ใครบางคนสามารถแทนที่ชั้นเรียนเพื่อสร้าง จำลอง / ทดสอบคอนโซล ...


4

อีกทางเลือกหนึ่งคือการสร้างวิธีการเพื่อสรุปทั้งสองตัวเลือกและ "ล้มเหลว" ไปยังเมธอด System.in เมื่อคอนโซลไม่พร้อมใช้งาน ตัวอย่างด้านล่างนี้เป็นขั้นตอนพื้นฐาน - คุณสามารถทำตามขั้นตอนเดียวกันนี้เพื่อสรุปวิธีการอื่น ๆ ใน Console (readPassword, format) ได้ตามต้องการ ด้วยวิธีนี้คุณสามารถเรียกใช้งานได้อย่างมีความสุขใน Eclipse และเมื่อนำไปใช้งานคุณจะได้รับคุณสมบัติคอนโซล (เช่นการซ่อนรหัสผ่าน) เริ่มใช้งาน

    private static String readLine(String prompt) {
        String line = null;
        Console c = System.console();
        if (c != null) {
             line = c.readLine(prompt);
        } else {
            System.out.print(prompt);
            BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(System.in));
            try {
                 line = bufferedReader.readLine();
            } catch (IOException e) { 
                //Ignore    
            }
        }
        return line;
    }

2

เท่าที่ฉันบอกได้ไม่มีวิธีรับวัตถุคอนโซลจาก Eclipse ฉันแค่ตรวจสอบให้แน่ใจว่า console! = null จากนั้น JAR ขึ้นและเรียกใช้จากบรรทัดคำสั่ง


1

ดูเหมือนจะไม่มีวิธีรับวัตถุ java.io.Console เมื่อเรียกใช้แอปพลิเคชันผ่าน Eclipse หน้าต่างคอนโซลบรรทัดคำสั่งไม่ได้เปิดขึ้นพร้อมกับแอ็พพลิเคชันเนื่องจากรันเป็นกระบวนการพื้นหลัง (พื้นหลังของ Eclipse?) ขณะนี้ไม่มีปลั๊กอิน Eclipse ที่จะจัดการปัญหานี้ส่วนใหญ่เกิดจาก java.io.Console เป็นคลาสสุดท้าย

สิ่งที่คุณทำได้จริงๆคือทดสอบออบเจ็กต์คอนโซลที่ส่งคืนสำหรับค่าว่างและดำเนินการต่อจากที่นั่น


1

นี้การเชื่อมโยงข้อเสนอทางเลือกในการใช้ System.Console () หนึ่งคือการใช้ BufferedReader ที่พันรอบ System.in อย่างที่สองคือใช้ Scanner ที่พันรอบ System.in

ไม่กระชับเท่าคอนโซล แต่ทั้งสองทำงานใน eclipse โดยไม่ต้องหันไปแก้ไขข้อบกพร่อง!


0

สมมติว่าพื้นที่ทำงาน Eclipse ของคุณคือ C: \ MyWorkspace คุณสร้างแอปพลิเคชัน java ของคุณภายใน MyProject โครงการ maven และคลาสหลัก Java ของคุณคือ com.mydomain.mypackage.MyClass

ในกรณีนี้คุณสามารถเรียกใช้คลาสหลักของคุณที่ใช้System.console()ในบรรทัดคำสั่ง:

java -cp C:\MyWorkspace\MyProject\target\classes com.mydomain.mypackage.MyClass

NB1: หากไม่ได้อยู่ในโครงการ maven ให้ตรวจสอบโฟลเดอร์ผลลัพธ์ในคุณสมบัติของโครงการ | เส้นทางการสร้าง Java | ที่มา อาจไม่ใช่ "เป้าหมาย / คลาส"

NB2: ถ้าเป็นโครงการ maven แต่ชั้นเรียนของคุณอยู่ใน src / test / java คุณอาจต้องใช้ "target \ test-class" แทน "target \ class"

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