java socket프로그래밍 관련 질문입니다.
글쓴이: ehyuck / 작성시간: 금, 2020/11/27 - 12:48오후
소켓 프로그래밍 관련 질문입니다. 멀티쓰레드 환경으로 여러개의 채팅방을 구현하려는 코드를 작성중입니다.
그래서 제가 구현한 방식은 client가 server에게 다른 client와 채팅요청을 하면 받아지면, 둘의 채팅방이 생겨서 서로 대화하는 형식입니다. 그 채팅방에서 친구를 추가할 수 있는 기능도 구현을 생각하고 있습니다. 하지만. 두명에서 1:1 채팅가지는 지금 되고 있는 상태인데, 3명부터는 채팅이 추가하지 않은 클라이언트에게java.lang.NullPointerException
오류가 나오고, 그 뒤로 소켓을 읽어오지 않습니다.(broadcast를 해주었음에도 불구하고)
server의 코드입니다.
package Mypackage;
import java.io.IOException;
import java.util.Iterator;
import java.sql.*;
import java.io.PrintWriter;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Set;
import java.util.HashSet;
import java.util.Scanner;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class LoginServer
{
private static Set<String> userlist = new HashSet<>(); //가입자들의 정보 저장.
private static Set<PrintWriter> writers = new HashSet<>();
private static Set<String> chatList = new HashSet<>();
public static void main(String[] args) throws Exception
{
System.out.println("The chat server is running...");
ExecutorService pool = Executors.newFixedThreadPool(500);
try (ServerSocket listener = new ServerSocket(59001))
{
while (true)
{
pool.execute(new Handler(listener.accept()));
}
}
}
private static class Handler implements Runnable
{
private String id;
private Socket socket;
private Scanner in;
private PrintWriter out;
private String pw;
private String logid="";
String DB_URL = "jdbc:mysql://localhost/userlist?serverTimezone=UTC"; //접속할 DB 서버
Connection conn=null;
Statement state=null;
public Handler(Socket socket)
{
this.socket = socket;
}
public void run()
{
try {
in = new Scanner(socket.getInputStream());
out = new PrintWriter(socket.getOutputStream(), true);
Class.forName("com.mysql.cj.jdbc.Driver"); //mysql driver
conn=DriverManager.getConnection(DB_URL,"root","jang14"); //db주소와, 사용자, 비밀번호를 통해서 접근.
state=conn.createStatement(); //mysql 연결
boolean realuser=false;
Statement state9=conn.createStatement();
String list="select userid from info";
ResultSet ulist=state9.executeQuery(list);//데이터베이스의 userid를 다 가져옴.
while(ulist.next())
{
userlist.add(ulist.getString("userid"));//데이터베이스에서 가져온 userid를 server의 hashlist에저장.
}
writers.add(out);
while(true)
{
String input=in.nextLine();
System.out.println(input);
if(input.startsWith("logid")) //client에서 logid가 왔을 때, 로그인
{
String[]info=input.split(" "); //id와 password가 같이와서 나눠줌.
id=info[0].substring(5); //id
pw=info[1]; //password
String sqlid="select userid from info where userid like"+"'"+id+"'";
ResultSet rsi=state.executeQuery(sqlid);
if ((rsi.next() == false || (id.isEmpty()) == true))
{
out.println("id invalid"); //로그인 실패
}
rsi.close();
Statement state2=conn.createStatement();
String sql="select * from info where userid like"+"'"+id+"'"; //id를 바탕으로 비밀번호를 찾음
ResultSet rs=state2.executeQuery(sql); //결과 값 저장.
Statement state3=conn.createStatement();
while(rs.next()) //데이터베이스 스캔
{
String dbpw=rs.getString("password"); //조건문에 맞는 패스워드 저장\
if(pw.equalsIgnoreCase(dbpw)) //입력한 비밀번호와 아이디가 맞을 때, 로그인성공
{
out.println("access:"+rs.getString("name")+":"+rs.getString("comment")+":"+id+":"+rs.getString("friend"));//클라이언트에게 성공했다고 보내줌.
String sql_update = "update info set login_count = login_count+1, status = true where userid = "+ "'"+id+"'";
state3.executeUpdate(sql_update);
logid=id; //로그인 되어있는 아이디 저장.
}
else
{
out.println("pw invalid"); //로그인 실패
}
}
rs.close();
state3.close();
state2.close();
}
else if(input.startsWith("Resister")) //회원가입
{
String [] nw=input.split(" "); //회원가입되서 온 정보를 나눠줌.
String addname=nw[0].substring(8);
int addbday=Integer.parseInt(nw[1]);
String addemail=nw[2];
String addid=nw[3];
String addpw=nw[4];
String addnick = nw[5];
Statement state4=conn.createStatement();
String mysql="insert into info values("+"'"+addname+"'"+","+addbday+","+"'"+addemail+"'"+","+"'"+addid+"'"+","+"'"+addpw+"'"+","+0+","+"'"+"hello world"+"'"+","+"'"+null+"'"+"," + "'"+addnick+"'"+","+false+","+"'2011210557'"+")";
//String mysql="insert into info values("+"'"+addname+"'"+","+addbday+","+"'"+addemail+"'"+","+"'"+addid+"'"+","+"'"+addpw+"'"+","+0+","+"'"+""+"'"+","+"'"+"hello world"+"'"+")";
//데이터베이스에 저장시켜주는 구문
state4.executeUpdate(mysql); //데이터베이스 업데이트
userlist.add(nw[3]); //가입하면, hashset에 userid 추가
out.println("Welcome"); //회원가입 되었다는 것을 보내줌.
state4.close();
}
else if(input.startsWith("Search"))//client에서 검색하라고 명령이 왓을경우
{
String sid=input.substring(6);
Iterator<String>finduser=userlist.iterator();
while(finduser.hasNext())
{
String comp=finduser.next();
if(sid.contains(comp))
{
realuser=true; //hashset에서 해당 가입자가 있는지 스캔
}
}
if(realuser==true) //가입자가 있을 경우 , 해당가입자의 정보 출력해서 client에게 보내줌.
{
String searchinfo="select * from info where userid like '"+sid+"'";//해당아이디의 정보를 찾음
Statement st2=null;
st2=conn.createStatement();
ResultSet sch=st2.executeQuery(searchinfo); //찾은 정보를 저장.
String fetch="";
while(sch.next())
{
fetch="Searching"+sch.getString("name")+" "+sch.getString("birthday")+" "+sch.getString("email")+" "+sch.getString("comment");
//찾은 정보를 보내줌.
}
System.out.println(fetch);
out.println(fetch);
st2.close();
realuser=false;
}
else if(realuser==false) //해당가입자가 없을 경우 client에게 보내줌.
{
out.println("No user");
}
}
else if(input.startsWith("ADDF")) //친구를 추가할때,
{
boolean check=false;
String take="select friend from info where userid like"+"'"+logid+"'"; //현재 로그인되어 있는 사용자의 친구명단을 읽어옴.
Statement state6=conn.createStatement();
ResultSet fri=state6.executeQuery(take);
String prev="";
while(fri.next())
{
prev=fri.getString("friend"); //그 전에 있던 친구명단을 가져옴.
}
String ptocol=input.substring(4); //추가할 친구id를 가져옴
Iterator <String> afinduser=userlist.iterator(); //친구로 추가할 id가 실제로 가입자인지 스캔
while(afinduser.hasNext())
{
String comp2=afinduser.next();
if(ptocol.contains(comp2))
{
check=true; //있으면 true로 바꿔줌
}
}
if(check==true) //가입자가 있을 경우, 친구 추가 진행
{
if(prev!=null&&prev.contains(ptocol)) { //친구리스트에 친구가 겹치는 경우
out.println("DUPLICATION");
}
else {
String flist=prev+" "+ptocol; //새로 친구리스트를 만들어줌
state6.close();
String fradd="update info set friend="+"'"+flist+"'"+"where userid like"+"'"+logid+"'"; //데이터베이스에 반영시켜줌
Statement state7=conn.createStatement();
state7.executeUpdate(fradd);
state7.close();
out.println("ADD"); //client에게 추가했다고 보내줌.
check=false;
}
}
else if(check==false) //가입자가 없을 경우, 사용자가 없다고 client에 보내줌.
{
out.println("No user");
}
}
else if(input.startsWith("List")) //client에서 친구 리스트가 필요하다고 왓을때
{
String obj=input.substring(4); //리스트가 필요한 로그인 사용자 id를 불러온다.
String comma="select friend from info where userid like"+"'"+obj+"'"; //해당 id의 친구 리스트 저장
Statement state8=conn.createStatement();
ResultSet frlist=state8.executeQuery(comma); //친구 리스트 조회
String temp="";
while(frlist.next())
{
temp=temp+frlist.getString("friend"); //temp에 친구리스트 저장
}
out.println("Frlist"+temp); //client에 친구리스트를 보내줌.
}
else if(input.startsWith("ChangeInfo")) { // 내정보 변경 할 때
String[] ch_info = input.split(":");
String ch_sql = "update info set nickname = "+"'"+ch_info[1]+"'," + " comment = " + "'"+ch_info[2]+"'"+" where userid = " +"'"+logid+"'";// 닉네임이랑 상태메시지 변경함
Statement state10 = conn.createStatement();
state10.executeUpdate(ch_sql);
state10.close();
}
else if(input.startsWith("chatting TEXT"))
{
String msg = input.substring(13);
String [] talk=msg.split(":");
for (PrintWriter writer : writers)
{
writer.println("Message" +talk[0]+ ": "+talk[1]);
}
}
else if(input.startsWith("LOGOUT"))
{
String logout_time = input.substring(6);
int time = Integer.parseInt(logout_time);
String time_update = "update info set time = " + "'"+time+"'" + ", status = false where userid = " + "'" + logid + "'";
Statement state11 = conn.createStatement();
state11.executeUpdate(time_update);
state11.close();
}
else if(input.startsWith("Start"))
{
String [] person = input.split(":");
//String person=input.substring(5);
for (PrintWriter writer : writers)
{
writer.println("Request:"+person[1]+":"+person[2]);//client에게 입장알림을 전달.
}
}
else if(input.startsWith("Nop"))
{
String cancel=input.substring(3);
for (PrintWriter writer : writers)
{
writer.println("Denied"+cancel);
}
}
else if(input.startsWith("Join"))
{
String chatter=input.substring(4);
chatList.add(chatter);
for (PrintWriter writer : writers)
{
writer.println("Message"+chatter+" has joined");
}
}
else if(input.startsWith("Exit"))
{
String end=input.substring(4);
String []already=end.split(":");
chatList.remove(already[0]);
for (PrintWriter writer : writers)
{
writer.println("Message"+already[0]+" "+"has exited");
}
}
else if(input.startsWith("Invite"))
{
boolean ivd=false;
String ivmsg=input.substring(6);
String [] ivperson=ivmsg.split(":");
Iterator<String>inviuser=userlist.iterator();
while(inviuser.hasNext())
{
String comp1=inviuser.next();
if(comp1.contains(ivperson[0]))
{
ivd=true; //hashset에서 해당 가입자가 있는지 스캔
}
}
if(ivd=true)
{
for (PrintWriter writer : writers)
{
writer.println("Invite:"+ivperson[0]+":"+ivperson[1]);
}
ivd=false;
}
else if(ivd==false)
{
for(PrintWriter writer: writers)
{
writer.println("No user");
}
}
}
out.flush();
}
}
catch (Exception e)
{
System.out.println(e);
}
finally {
if (out != null)
{
}
try { socket.close(); }
catch (IOException e){}
}
}
}
}클라이언트 코드입니다.
package Mypackage;
import java.awt.event.ActionEvent;
import java.util.Date;
import java.text.SimpleDateFormat;
import java.awt.event.MouseEvent;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener;
import java.awt.event.MouseAdapter;
import java.awt.event.ActionListener;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Arrays;
import java.util.HashSet;
import java.util.Hashtable;
import java.util.Scanner;
import java.util.Set;
import java.awt.*;
import javax.swing.*;
import javax.swing.border.*;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.net.*;
import java.awt.event.MouseEvent;
import java.awt.event.MouseAdapter;
import javax.swing.ListSelectionModel;
import javax.swing.ListModel;
import javax.swing.SwingConstants;
import Mypackage.SocialDate;
public class Login
{
//
static String ip=null; //txt파일에서, ip읽어옴.
static int portnum=0; //port number
String serverAddress; //서버 주소
Scanner in;
PrintWriter out;
String curid; //현재 로그인 id
//login gui variables
JFrame frame=new JFrame("login form");
JLabel lbl,la1,la2,la3,emp;
JTextField id;
JPasswordField passwd;
JPanel emptyPanel,idPanel,paPanel,loginPanel;
JButton b1,b2;
JTextArea content;
//TODO:
//메뉴창
JFrame menu_frame;
JLabel user_name;
JLabel user_state;
JPanel menu_p;
JButton make_room;
JButton add_friend;
JList friend_list;
DefaultListModel friend_model;
JButton change_info;
JPopupMenu popupMenu;
JMenuItem lookinfo;
JMenuItem sendMsg;
//채팅방 swing 변수
JFrame room_frame;
JTextField sendTF; //보낼 메시지 적는 곳
JLabel la_msg;
JTextArea ta; //메시지가 쌓여서 보이는 곳
JScrollPane sp_ta,sp_list;
JList<String> user; // 현재 채팅방에 있는 유저 표시
JButton invite_btn,exit_btn; //초대 나가기 버튼
JPanel p;
//추가하려는 친구
String relaid;
public String encryptSHA256(String str) {
String sha="";
try { MessageDigest sh= MessageDigest.getInstance("SHA-256");
sh.update(str.getBytes());
byte[] byteData = sh.digest();
StringBuilder sb=new StringBuilder();
for (byte byteDatum : byteData) {
sb.append(Integer.toString((byteDatum & 0xff) + 0x100, 16).substring(1));
}
sha=sb.toString(); }
catch (NoSuchAlgorithmException e) {
System.out.println("암호화 에러-NoSuchAlgorithmException");
sha=null;
}
return sha;
}
public Login(String serverAddress)
{
this.serverAddress=serverAddress;
// FlowLayout사용
frame.setLayout( new FlowLayout() );
// Border로 영역 생성
EtchedBorder eborder = new EtchedBorder();
// 레이블 생성
lbl = new JLabel( "Enter Id and Password" );
// 레이블에 영역 만들기
lbl.setBorder(eborder);
// 레이블 추가
frame.add(lbl);
emptyPanel = new JPanel();
emp = new JLabel("\n");
emptyPanel.add(emp);
frame.add(emp);
// id패널과 pw 패널생성
idPanel = new JPanel();
paPanel = new JPanel();
la3 = new JLabel("Username");
la2 = new JLabel(" Password");
// id텍스트필드와 pw텍스트 필드 선언
id = new JTextField(20);
passwd = new JPasswordField(20);
idPanel.add(la3);
idPanel.add(id);
paPanel.add(la2);
paPanel.add(passwd);
// 로그인과 회원가입을 위한 패널 생성
loginPanel = new JPanel();
b1 = new JButton("Login");
b2 = new JButton("Resister");
loginPanel.add(emp);
loginPanel.add(b1);
loginPanel.add(b2);
frame.add(emptyPanel);
frame.add(emptyPanel);
frame.add(idPanel);
frame.add(paPanel);
frame.add(emptyPanel);
frame.add(loginPanel);
b1.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
String comment=e.getActionCommand();
if(comment.contentEquals("Login")) //로그인 버튼을 눌렀을 때,
{
String logid= id.getText().trim(); //id에 누른 값을 불러옴
String logpw= passwd.getText(); //패스워드에 누른 값을 불러옴.
String encryptLogPW = encryptSHA256(logpw);
out.println("logid"+logid+" "+encryptLogPW); //서버에게 아이디와 패스워드 전달
if(logid.length()==0 || logpw.length()==0)
{
JOptionPane.showMessageDialog(null, "아이디 또는 비밀번호를 입력 하셔야 됩니다.", "아이디나 비번을 입력!", JOptionPane.DEFAULT_OPTION);
return;
}
frame.dispose();
}
}
});
b2.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
new Resister();
}
});
// 3행 20열 영역의 텍스트에어리어
//content = new JTextArea(3,20);
//JScrollPane s= new JScrollPane(content);
//add(s);
frame.setSize( 400, 200 );
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
public class Resister {
JFrame sub=new JFrame("Resister");
JLabel lbl,namelbl,birthlbl,emaillbl, idlbl,pwlbl,nicklbl;
JTextField nameField, birthField,emailField, idField, nickField;
JPasswordField passwd;
JPanel namePanel,birthPanel, emailPanel, idPanel,paPanel,nickPanel;
JButton resister_btn;
JTextArea content;
public Resister() {
sub.setLayout(new FlowLayout());
EtchedBorder eborder = new EtchedBorder();
lbl = new JLabel( "Enter user information" );
// 레이블에 영역 만들기
lbl.setBorder(eborder);
sub.add( lbl );
namePanel = new JPanel();
birthPanel = new JPanel();
emailPanel = new JPanel();
idPanel = new JPanel();
paPanel = new JPanel();
nickPanel = new JPanel();
namelbl = new JLabel("User Name");
nameField = new JTextField(10);
namePanel.add(namelbl);
namePanel.add(nameField);
sub.add(namePanel);
birthlbl = new JLabel("birthday");
birthField = new JTextField(10);
birthPanel.add(birthlbl);
birthPanel.add(birthField);
sub.add(birthPanel);
emaillbl = new JLabel("email");
emailField = new JTextField(10);
emailPanel.add(emaillbl);
emailPanel.add(emailField);
sub.add(emailPanel);
idlbl = new JLabel("user Id");
idField = new JTextField(10);
idPanel.add(idlbl);
idPanel.add(idField);
sub.add(idPanel);
pwlbl = new JLabel("password");
passwd = new JPasswordField(10);
paPanel.add(pwlbl);
paPanel.add(passwd);
sub.add(paPanel);
nicklbl = new JLabel("nick name");
nickField = new JTextField(10);
nickPanel.add(nicklbl);
nickPanel.add(nickField);
sub.add(nickPanel);
resister_btn = new JButton("Resister");
sub.add(resister_btn);
resister_btn.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
String comment=e.getActionCommand();
if(comment.contentEquals("Resister")) //register버튼 입력시,
{
String name=nameField.getText(); //이름, 생년월일등을 불러옴
String bday=birthField.getText();
String email=emailField.getText();
String id=idField.getText();
String pw=passwd.getText();
String encryptPW = encryptSHA256(pw);
String nick = nickField.getText();
out.println("Resister"+name+" "+bday+" "+email+" "+id+" "+encryptPW + " " + nick); //서버에게 전달.
}
sub.dispose();
}
});
sub.setSize( 250, 350 );
sub.setVisible(true);
sub.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}
//TODO:
public class Chatting_Room {
public Chatting_Room(String id) {
room_frame = new JFrame(id+"'s chatting room");
sendTF = new JTextField(15);
la_msg = new JLabel("Message");
ta = new JTextArea();
ta.setLineWrap(true);//TextArea 가로길이를 벗어나는 text발생시 자동 줄바꿈
user = new JList<String>();
sp_ta = new JScrollPane(ta);
sp_list = new JScrollPane(user);
invite_btn = new JButton("친구 초대");
exit_btn = new JButton("나가기");
p = new JPanel();
sp_ta.setBounds(10,10,380,390);
la_msg.setBounds(10,410,60,30);
sendTF.setBounds(70,410,320,30);
sp_list.setBounds(400,10,120,350);
invite_btn.setBounds(400,370,120,30);
exit_btn.setBounds(400,410,120,30);
p.setLayout(null);
p.setBackground(Color.GRAY);
p.add(sp_ta);
p.add(la_msg);
p.add(sendTF);
p.add(sp_list);
p.add(invite_btn);
p.add(exit_btn);
sendTF.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
out.println("chatting TEXT"+curid+":"+sendTF.getText());
sendTF.setText("");
}
});
exit_btn.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
if (e.getSource() == exit_btn)
room_frame.dispose();
}
});
invite_btn.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e)
{
if(e.getSource()==invite_btn)
{
new Invite(curid);
}
}
});
room_frame.add(p);
room_frame.setBounds(300,200,550,500);
room_frame.setVisible(true);
room_frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
sendTF.requestFocus();
}
}
//TODO:
public class Menu {
public Menu(String name, String comment, String friend) {
popupMenu = new JPopupMenu();
lookinfo = new JMenuItem("친구정보보기");
sendMsg = new JMenuItem("채팅신청하기");
popupMenu.add(lookinfo);
popupMenu.add(sendMsg);
menu_frame = new JFrame("Menu");
user_name = new JLabel(name);
user_state = new JLabel(comment);
make_room = new JButton("방 만들기");
add_friend=new JButton("친구검색");
friend_list = new JList(new DefaultListModel());
friend_model = (DefaultListModel)friend_list.getModel();
for(String add:friend.split(" ")) {
friend_model.addElement(add);
}
friend_list.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
friend_list.addMouseListener(new MouseAdapter() {
@Override
public void mousePressed(MouseEvent e) {
// 오른쪽 버튼 클릭 시 ...
if(e.getModifiers() == MouseEvent.BUTTON3_MASK) { // 왼쪽이 1 가운데가 2 오른쪽이 3 BUTTON3_MASK - 오른쪽 버튼
// System.out.println("반응");
popupMenu.show(friend_list, e.getX(), e.getY());
friend_list = (JList)e.getSource();
}
}
});
lookinfo.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e)
{
String comm=e.getActionCommand();
if(comm.contentEquals("친구정보보기"))
{
String str = (String)friend_list.getSelectedValue();
out.println("Search"+str);
}
}
});
sendMsg.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
String start=e.getActionCommand();
if(start.contentEquals("채팅신청하기"))
{
Chatting_Room c1=new Chatting_Room(curid);
String receiver=(String)friend_list.getSelectedValue();
out.println("Start:"+receiver+":"+curid);
System.out.println(receiver);
}
}
});
friend_model.remove(0); // db에 저장된 친구이름이 null로 시작해서 앞에 null 지워줌
change_info = new JButton("정보 수정");
user_name.setBounds(10, 50, 150, 20);
user_state.setBounds(10, 80, 350, 15);
make_room.setBounds(200, 400, 120, 30);
add_friend.setBounds(10, 10, 120, 30);
friend_list.setBounds(10, 110, 350, 130);
change_info.setBounds(150, 10, 120,30);
menu_p = new JPanel();
menu_p.setLayout(null);
menu_p.add(add_friend);
menu_p.add(change_info);
menu_p.add(user_name);
menu_p.add(user_state);
menu_p.add(friend_list);
menu_frame.add(menu_p);
menu_frame.setSize(400,300);
menu_frame.setVisible(true);
//동네예보
SocialDate s = new SocialDate();
JPanel data_p = new JPanel();
data_p.setBackground(Color.GRAY);
data_p.setLayout(null);
JLabel locationlbl = new JLabel("성남시 수정구 기준시간 : 00시");
locationlbl.setBounds(10,300,300,50);
JLabel t1hlbl = new JLabel("기온");
JLabel t1hlbl2 = new JLabel(s.tem);
JLabel rehlbl = new JLabel("습도");
JLabel rehlbl2 = new JLabel(s.hum);
t1hlbl.setBounds(10, 350, 150, 50);
t1hlbl2.setBounds(60, 350, 150,50);
data_p.add(t1hlbl);
data_p.add(t1hlbl2);
rehlbl.setBounds(10, 400,150,50);
rehlbl2.setBounds(60,400,150,50);
data_p.add(rehlbl);
data_p.add(rehlbl2);
data_p.add(locationlbl);
data_p.setSize(400,200);
menu_frame.add(data_p);
menu_frame.setSize(400,500);
menu_frame.setVisible(true);
menu_frame.addWindowListener(new WindowListener() {
@Override
public void windowClosed(WindowEvent e) {
}
@Override
public void windowOpened(WindowEvent e) {
}
@Override
public void windowClosing(WindowEvent e) {
//String date
Date date = new Date();
SimpleDateFormat sdf = new SimpleDateFormat("yyMMddhhmm");
out.println("LOGOUT"+ sdf.format(date));
}
@Override
public void windowIconified(WindowEvent e) {
}
@Override
public void windowDeiconified(WindowEvent e) {
}
@Override
public void windowActivated(WindowEvent e) {
}
@Override
public void windowDeactivated(WindowEvent e) {
}
});
add_friend.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e)
{
new Addfr();
}
});
change_info.addActionListener(new ActionListener() { // 메뉴에서 정보변경 버튼 누르면
@Override
public void actionPerformed(ActionEvent e) {
new ChangeInfo();
}
});
}
}
public class Invite //로그인해서, user를 검색하는창
{
public Invite(String id)
{
JFrame iadder=new JFrame();
iadder.setTitle("초대하실 id를 입력해주세요.");
iadder.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
iadder.setLayout(new FlowLayout());
JLabel inviid=new JLabel("아이디");
JTextField iid=new JTextField(20);
iadder.add(inviid);
iadder.add(iid);
iadder.setSize(300,150);
iadder.setVisible(true);
JButton invitefr=new JButton("초대");
JPanel pnr=new JPanel();
pnr.add(invitefr);
iadder.add(pnr,BorderLayout.SOUTH);
invitefr.addActionListener(new ActionListener() //text로 정보를 확인하고, 친구를 추가함.
{
public void actionPerformed(ActionEvent e)
{
String comment=e.getActionCommand();
if(comment.contentEquals("초대"))
{
String inviname=iid.getText(); //텍스트창에서 문서를 받아온다
out.println("Invite"+inviname+":"+id);
iadder.dispose();
}
}
});
}
}
public class Addfr //로그인해서, user를 검색하는창
{
public Addfr()
{
JFrame adder=new JFrame();
adder.setTitle("친구 검색");
adder.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
adder.setLayout(new FlowLayout());
JLabel searid=new JLabel("아이디");
JTextField uid=new JTextField(20);
adder.add(searid);
adder.add(uid);
adder.setSize(300,150);
adder.setVisible(true);
JButton search=new JButton("검색");
JButton add=new JButton("추가");
JButton list=new JButton("친구리스트");
JPanel pnr=new JPanel();
pnr.add(search);
pnr.add(add);
pnr.add(list);
adder.add(pnr,BorderLayout.SOUTH);
search.addActionListener(new ActionListener() //text를 작성하고, 검색을 함.
{
public void actionPerformed(ActionEvent e)
{
String comment=e.getActionCommand();
if(comment.contentEquals("검색"))
{
String conveyid=uid.getText(); //텍스트창에서 문서를 받아온다
out.println("Search"+conveyid);//서버에 검색하는 아이디를 전달.
}
}
});
add.addActionListener(new ActionListener() //text로 정보를 확인하고, 친구를 추가함.
{
public void actionPerformed(ActionEvent e)
{
String comment=e.getActionCommand();
if(comment.contentEquals("추가"))
{
relaid=uid.getText(); //텍스트창에서 문서를 받아온다
out.println("ADDF"+relaid);//서버에 추가하려는 id를 보낸다.
}
}
});
list.addActionListener(new ActionListener() //text로 정보를 확인하고, 친구를 추가함.
{
public void actionPerformed(ActionEvent e)
{
String comment=e.getActionCommand();
if(comment.contentEquals("친구리스트"))
{
out.println("List"+curid);
}
}
});
}
}
public class ChangeInfo{ //내정보 변경하는 창
public ChangeInfo() {
JFrame ch_frame=new JFrame();
JPanel ch_panel = new JPanel();
ch_panel.setLayout(null);
ch_frame.setTitle("내 정보 변경");
JLabel nicklbl2 = new JLabel( "Nick Name");
JTextField nickField2 = new JTextField(50); //바꿀 닉네임
JLabel commentlbl = new JLabel("Comment");
JTextField commentField = new JTextField(50); // 바꿀 상태 메시지
JButton ch_btn = new JButton("정보 변경"); // 정보 변경 버튼 누르면 바꾸고자 하는 정보가 반영됨
nicklbl2.setBounds(10,10,100,30);
nickField2.setBounds(130, 10, 300,30);
ch_panel.add(nickField2);
ch_panel.add(nicklbl2);
commentlbl.setBounds(10,80,100,30);
commentField.setBounds(130, 80, 300,30);
ch_panel.add(commentlbl);
ch_panel.add(commentField);
ch_btn.setBounds(330,120,100,30);
ch_panel.add(ch_btn);
ch_frame.add(ch_panel);
ch_frame.setSize(500,200);
ch_frame.setVisible(true);
ch_btn.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
String ch_nick = nickField2.getText();
String ch_comment = commentField.getText();
out.println("ChangeInfo:"+ch_nick+":"+ch_comment); // 바꿀 내용 서버에 알림
user_state.setText(ch_comment); // 바꾼 내용을 메뉴 칸에 반영함
ch_frame.dispose();
}
});
}
}
private void run() {
try {
Socket socket = new Socket(serverAddress, portnum); //입력받은 ip주소와 portnumber로 소켓 생성.
in = new Scanner(socket.getInputStream());
out = new PrintWriter(socket.getOutputStream(), true);
String[] userinfo = null;
while(true)
{
String line=in.nextLine();
System.out.println(line);
if(line.contains("access"))
{
userinfo = line.split(":");
JOptionPane.showMessageDialog(null, "로그인 성공", "로그인 확인!", JOptionPane.DEFAULT_OPTION);//서버가 로그인 성공이라고 했을 시, 창 표출
//TODO:
new Menu(userinfo[1],userinfo[2],userinfo[4]);
curid=userinfo[3];
}
// 아이디가 틀렸을 때
else if(line.contains("id invalid"))
{
JOptionPane.showMessageDialog(null, "아이디 틀림!", "로그인 확인!", JOptionPane.DEFAULT_OPTION); //로그인 실패 시, 창표출
return;
}
// 비밀번호가 틀렸을 때
else if(line.contains("pw invalid"))
{
JOptionPane.showMessageDialog(null, "비밀번호 틀림!", "로그인 확인!", JOptionPane.DEFAULT_OPTION); //로그인 실패 시, 창표출
return;
}
else if(line.contains("Welcome"))
{
JOptionPane.showMessageDialog(null, "회원가입성공", "환영합니다!", JOptionPane.DEFAULT_OPTION); //회원가입 성공 시, 창표출
return;
}
else if(line.contains("Searching")) //검색한 정보를 받았을 때,
{
String printinfo=line.substring(9); //정보 뽑아냄
String [] showbox=printinfo.split(" ");
String wholeinfo="";
wholeinfo="name"+":"+showbox[0]+"\n"+"birthday"+":"+showbox[1]+"\n"+"email"+":"+showbox[2]+"\n"+"comment"+":"+showbox[3];
JOptionPane.showMessageDialog(null, wholeinfo, "검색하신 정보는 위와 같습니다.", JOptionPane.DEFAULT_OPTION);
//묶은 정보를 출력.
}
else if(line.contains("ADD")) //친구 추가완료됨
{
JOptionPane.showMessageDialog(null, "친구추가완료", "축하합니다", JOptionPane.DEFAULT_OPTION); //친구추가된 경우, 창표출
friend_model.addElement(relaid);
}
else if(line.contains("DUPLICATION"))
{
JOptionPane.showMessageDialog(null, "이미 추가된 친구입니다.", "친구 추가 실패",JOptionPane.DEFAULT_OPTION);// 친구가 중복된 경우
}
else if(line.contains("Frlist")) //server가 친구리스트를 보내줬을 때.
{
String flend=line.substring(6); //친구리스트를 문자열화
String [] flist=flend.split(" "); //친구리스트가 한꺼번에 왔기 때문에, 쪼개준다.
String ourfr="";
for(int i=0; i<flist.length;i++)
{
ourfr=ourfr+flist[i]+"\n"; //ourfr에 친구리스트 쪼개서 저장
}
JOptionPane.showMessageDialog(null, ourfr, "고객님의 친구명단은 아래와 같습니다", JOptionPane.DEFAULT_OPTION); //친구명단을 임시로 창표출
return; //친구리스트 출력.
}
else if(line.contains("No user")) //server에서, 해당 사용자가 없다고 왓을 경우 오류 출력.
{
JOptionPane.showMessageDialog(null, "존재하지 않는 아이디입니다.", "error ", JOptionPane.DEFAULT_OPTION); //친구명단을 임시로 창표출
}
else if(line.contains("Message"))
{
sendTF.setEditable(true);
String msg = line.substring(7);
ta.append(msg + "\n");
}
else if(line.contains("Request"))
{
String ifo=line.substring(8);
String [] temp=ifo.split(":");
String rcv=temp[0];
String snd=temp[1];
if(rcv.equalsIgnoreCase(curid)==true)
{
int result=JOptionPane.showConfirmDialog(null,
snd+"으로부터 요청이 왔습니다", "confirm",
JOptionPane.YES_NO_OPTION);
if(result == JOptionPane.NO_OPTION)
{
out.println("Nop"+snd+" "+"reject the chatting");
}
else if(result == JOptionPane.YES_OPTION)
{
new Chatting_Room(rcv);
out.println("Join"+rcv);
}
}
}
else if(line.startsWith("Invite"))
{
String [] tmp=line.split(":");
System.out.println(tmp[1]);
System.out.println(curid);
if(curid.equalsIgnoreCase(tmp[1])==true)
{
int result2=JOptionPane.showConfirmDialog(null,
tmp[2]+"으로부터 요청이 왔습니다", "confirm",
JOptionPane.YES_NO_OPTION);
if(result2 == JOptionPane.NO_OPTION)
{
out.println("Nop"+tmp[2]+" "+"reject the chatting");
}
else if(result2 == JOptionPane.YES_OPTION)
{
new Chatting_Room(tmp[1]);
out.println("Join"+tmp[1]);
}
}
}
else if(line.contains("Denied"))
{
ta.append(line.substring(6));
}
}
}
catch(Exception e)
{
System.out.println(e);
}
finally {
frame.dispose();
}
}
public static void server(String fileName) //input.txt파일에서 ip주소와 port number를 불러오는 함수.
{
Scanner inputStream = null;
try
{
inputStream = new Scanner(new File(fileName));//input파일을 읽어옴.
}
catch (FileNotFoundException e) //파일이 없을 경우, 자동생성
{
ip = "localhost";
portnum = 9999;
e.printStackTrace();
}
while (inputStream.hasNext()) //input파일에서, ip주소와 portnumber를 읽어옴.
{
ip = inputStream.next();
portnum = inputStream.nextInt();
}
}
public static void main(String args[])
{
String fname="input.txt";
server(fname); // input내용으로 정보 불러오기
Login client=new Login(ip);
client.run();
}
}Forums:


댓글 달기