@ -7,20 +7,33 @@ import com.fr.design.EnvChangeEntrance;
import com.fr.design.dialog.FineJOptionPane ;
import com.fr.design.dialog.FineJOptionPane ;
import com.fr.design.env.DesignerWorkspaceInfo ;
import com.fr.design.env.DesignerWorkspaceInfo ;
import com.fr.design.env.DesignerWorkspaceInfoContext ;
import com.fr.design.env.DesignerWorkspaceInfoContext ;
import com.fr.design.gui.ilable.UILabel ;
import com.fr.design.i18n.Toolkit ;
import com.fr.design.i18n.Toolkit ;
import com.fr.design.layout.FRGUIPaneFactory ;
import com.fr.design.mainframe.DesignerContext ;
import com.fr.design.mainframe.DesignerContext ;
import com.fr.design.mainframe.loghandler.DesignerLogger ;
import com.fr.design.mainframe.loghandler.DesignerLogger ;
import com.fr.design.mainframe.share.ui.base.MouseClickListener ;
import com.fr.design.mainframe.toast.DesignerToastMsgUtil ;
import com.fr.design.mainframe.toast.ToastMsgDialog ;
import com.fr.design.ui.util.UIUtil ;
import com.fr.design.ui.util.UIUtil ;
import com.fr.design.utils.BrowseUtils ;
import com.fr.event.EventDispatcher ;
import com.fr.event.EventDispatcher ;
import com.fr.general.CloudCenter ;
import com.fr.general.ComparatorUtils ;
import com.fr.general.ComparatorUtils ;
import com.fr.log.FineLoggerFactory ;
import com.fr.log.FineLoggerFactory ;
import com.fr.report.RemoteDesignConstants ;
import com.fr.report.RemoteDesignConstants ;
import com.fr.serialization.SerializerHelper ;
import com.fr.serialization.SerializerHelper ;
import com.fr.stable.ArrayUtils ;
import com.fr.stable.ArrayUtils ;
import com.fr.stable.StableUtils ;
import com.fr.stable.StringUtils ;
import com.fr.stable.StringUtils ;
import com.fr.third.apache.log4j.spi.LoggingEvent ;
import com.fr.third.apache.log4j.spi.LoggingEvent ;
import com.fr.third.org.apache.http.client.config.RequestConfig ;
import com.fr.third.org.apache.http.client.methods.CloseableHttpResponse ;
import com.fr.third.org.apache.http.client.methods.HttpGet ;
import com.fr.third.org.apache.http.conn.ssl.NoopHostnameVerifier ;
import com.fr.third.org.apache.http.conn.ssl.NoopHostnameVerifier ;
import com.fr.third.org.apache.http.conn.ssl.TrustSelfSignedStrategy ;
import com.fr.third.org.apache.http.conn.ssl.TrustSelfSignedStrategy ;
import com.fr.third.org.apache.http.impl.client.CloseableHttpClient ;
import com.fr.third.org.apache.http.impl.client.HttpClients ;
import com.fr.third.org.apache.http.ssl.SSLContexts ;
import com.fr.third.org.apache.http.ssl.SSLContexts ;
import com.fr.web.WebSocketConfig ;
import com.fr.web.WebSocketConfig ;
import com.fr.web.socketio.WebSocketProtocol ;
import com.fr.web.socketio.WebSocketProtocol ;
@ -29,7 +42,6 @@ import com.fr.workspace.Workspace;
import com.fr.workspace.base.WorkspaceConstants ;
import com.fr.workspace.base.WorkspaceConstants ;
import com.fr.workspace.connect.WorkspaceConnection ;
import com.fr.workspace.connect.WorkspaceConnection ;
import com.fr.workspace.connect.WorkspaceConnectionInfo ;
import com.fr.workspace.connect.WorkspaceConnectionInfo ;
import com.fr.workspace.server.socket.SocketInfoOperator ;
import io.socket.client.IO ;
import io.socket.client.IO ;
import io.socket.client.Socket ;
import io.socket.client.Socket ;
import io.socket.emitter.Emitter ;
import io.socket.emitter.Emitter ;
@ -38,15 +50,21 @@ import io.socket.engineio.client.transports.Polling;
import io.socket.engineio.client.transports.WebSocket ;
import io.socket.engineio.client.transports.WebSocket ;
import java.io.File ;
import java.io.File ;
import java.io.FileInputStream ;
import java.io.FileInputStream ;
import java.net.URL ;
import java.security.KeyStore ;
import java.security.KeyStore ;
import java.util.Arrays ;
import java.util.Arrays ;
import javax.net.ssl.SSLContext ;
import javax.net.ssl.SSLContext ;
import javax.swing.* ;
import javax.swing.BorderFactory ;
import javax.swing.JOptionPane ;
import javax.swing.JPanel ;
import javax.swing.UIManager ;
import java.awt.BorderLayout ;
import java.awt.Color ;
import java.awt.Cursor ;
import java.awt.event.MouseEvent ;
import java.io.IOException ;
import java.io.IOException ;
import java.net.URI ;
import java.net.URI ;
import java.net.URL ;
import java.util.Timer ;
import java.util.Timer ;
import java.util.TimerTask ;
public class DesignerSocketIO {
public class DesignerSocketIO {
@ -56,18 +74,21 @@ public class DesignerSocketIO {
Disconnecting
Disconnecting
}
}
private static final String WEBSOCKET_HELP_DOC = CloudCenter . getInstance ( ) . acquireUrlByKind ( "websocketConnect" , "https://help.fanruan.com/finereport/doc-view-2512.html" ) ;
private static final String HTTPS = "https" ;
private static final String HTTPS = "https" ;
private static final String HTTP = "http" ;
private static final String HTTP = "http" ;
private static Socket socket = null ;
private static Socket socket = null ;
private static Status status = Status . Disconnected ;
private static Status status = Status . Disconnected ;
private static Timer disConnectHintTimer = null ;
private static Timer disConnectHintTimer = null ;
private static long disConnectHintTimerDelay = 3000 ;
private static long disConnectHintTimerDelay = 3000 ;
private static final int TIMEOUT = 5000 ;
//维护一个当前工作环境的uri列表
//维护一个当前工作环境的uri列表
private static String [ ] uri ;
private static String [ ] uri ;
//维护一个关于uri列表的计数器
//维护一个关于uri列表的计数器
private static int count ;
private static int count ;
// 当前webSocket选择的协议
// 当前webSocket选择的协议
private static String currentProtocol ;
private static String currentProtocol ;
private static ToastMsgDialog dialog = null ;
public static void close ( ) {
public static void close ( ) {
@ -109,6 +130,7 @@ public class DesignerSocketIO {
} else {
} else {
//表示所有的uri都连接不成功
//表示所有的uri都连接不成功
FineLoggerFactory . getLogger ( ) . warn ( "All uris failed to connect" ) ;
FineLoggerFactory . getLogger ( ) . warn ( "All uris failed to connect" ) ;
showSocketDisconnectToast ( ) ;
}
}
} catch ( Exception e ) {
} catch ( Exception e ) {
FineLoggerFactory . getLogger ( ) . error ( e . getMessage ( ) , e ) ;
FineLoggerFactory . getLogger ( ) . error ( e . getMessage ( ) , e ) ;
@ -227,41 +249,35 @@ public class DesignerSocketIO {
@Override
@Override
public void call ( Object . . . objects ) {
public void call ( Object . . . objects ) {
FineLoggerFactory . getLogger ( ) . info ( "start disConnectHintTimer" ) ;
FineLoggerFactory . getLogger ( ) . info ( "start disConnectHintTimer" ) ;
disConnectHintTimer = new Timer ( ) ;
/ *
disConnectHintTimer . schedule ( new TimerTask ( ) {
* todo 远程心跳断开不一定 socket 断开 和远程紧密相关的业务都绑定在心跳上 , 切换成心跳断开之后进行提醒 ,
@Override
* socket 只用推日志和通知配置变更
public void run ( ) {
* /
try {
printLog ( objects , PrintEventLogImpl . ERROR , "disConnected args: {}" ) ;
/ *
if ( status ! = Status . Disconnecting ) {
* todo 远程心跳断开不一定 socket 断开 和远程紧密相关的业务都绑定在心跳上 , 切换成心跳断开之后进行提醒 ,
dealWithSocketDisconnect ( ) ;
* socket 只用推日志和通知配置变更
}
* /
status = Status . Disconnected ;
printLog ( objects , PrintEventLogImpl . ERROR , "disConnected args: {}" ) ;
if ( status ! = Status . Disconnecting ) {
showConnectionLostDialog ( ) ;
}
status = Status . Disconnected ;
} finally {
disConnectHintTimer . cancel ( ) ;
disConnectHintTimer = null ;
}
}
} , disConnectHintTimerDelay ) ;
}
}
} ;
} ;
private static void showConnectionLostDialog ( ) {
private static void dealWithSocketDisconnect ( ) {
if ( checkRPCConnect ( ) ) {
showSocketDisconnectToast ( ) ;
} else {
showRPCDisconnectDialog ( ) ;
}
}
private static void showSocketDisconnectToast ( ) {
try {
try {
UIUtil . invokeLaterIfNeeded ( new Runnable ( ) {
UIUtil . invokeLaterIfNeeded ( new Runnable ( ) {
@Override
@Override
public void run ( ) {
public void run ( ) {
FineJOptionPane . showMessageDialog (
if ( dialog = = null | | ! dialog . isShow ( ) ) {
DesignerContext . getDesignerFrame ( ) ,
dialog = DesignerToastMsgUtil . createPromptDialog ( createDialogContent ( ) ) ;
Toolkit . i18nText ( "Fine-Design_Basic_Remote_Disconnected" ) ,
dialog . setVisible ( true ) ;
UIManager . getString ( "OptionPane.messageDialogTitle" ) ,
}
JOptionPane . ERROR_MESSAGE ,
UIManager . getIcon ( "OptionPane.errorIcon" ) ) ;
EnvChangeEntrance . getInstance ( ) . chooseEnv ( ) ;
}
}
} ) ;
} ) ;
} catch ( Exception e ) {
} catch ( Exception e ) {
@ -269,6 +285,57 @@ public class DesignerSocketIO {
}
}
}
}
private static JPanel createDialogContent ( ) {
JPanel jPanel = FRGUIPaneFactory . createBorderLayout_S_Pane ( ) ;
jPanel . add ( new UILabel ( Toolkit . i18nText ( "Fine-Design_WebSocket_Lost_Tip" ) ) , BorderLayout . WEST ) ;
UILabel hyperLinkLabel = new UILabel ( Toolkit . i18nText ( "Fine-Design_WebSocket_Lost_Tip_HyperLink_Text" ) ) ;
hyperLinkLabel . addMouseListener ( new MouseClickListener ( ) {
@Override
public void mouseClicked ( MouseEvent e ) {
BrowseUtils . browser ( WEBSOCKET_HELP_DOC ) ;
}
} ) ;
hyperLinkLabel . setBorder ( BorderFactory . createEmptyBorder ( 0 , 3 , 0 , 0 ) ) ;
hyperLinkLabel . setForeground ( Color . BLUE ) ;
hyperLinkLabel . setCursor ( Cursor . getPredefinedCursor ( Cursor . HAND_CURSOR ) ) ;
jPanel . add ( hyperLinkLabel , BorderLayout . CENTER ) ;
return jPanel ;
}
private static void showRPCDisconnectDialog ( ) {
UIUtil . invokeLaterIfNeeded ( new Runnable ( ) {
@Override
public void run ( ) {
FineJOptionPane . showMessageDialog (
DesignerContext . getDesignerFrame ( ) ,
Toolkit . i18nText ( "Fine-Design_Basic_Remote_Disconnected" ) ,
UIManager . getString ( "OptionPane.messageDialogTitle" ) ,
JOptionPane . ERROR_MESSAGE ,
UIManager . getIcon ( "OptionPane.errorIcon" ) ) ;
EnvChangeEntrance . getInstance ( ) . chooseEnv ( ) ;
}
} ) ;
}
private static boolean checkRPCConnect ( ) {
CloseableHttpClient httpclient = HttpClients . createDefault ( ) ;
WorkspaceConnectionInfo info = getConnectionInfo ( ) ;
HttpGet httpGet = new HttpGet ( StableUtils . pathJoin ( info . getUrl ( ) , WorkspaceConstants . CONTROLLER_PREFIX , WorkspaceConstants . VT ) ) ;
RequestConfig requestConfig = RequestConfig
. custom ( )
. setConnectTimeout ( TIMEOUT )
. setConnectionRequestTimeout ( TIMEOUT )
. build ( ) ;
httpGet . setConfig ( requestConfig ) ;
try {
CloseableHttpResponse response = httpclient . execute ( httpGet ) ;
} catch ( Exception e ) {
FineLoggerFactory . getLogger ( ) . error ( e , e . getMessage ( ) ) ;
return false ;
}
return true ;
}
//配置变更监听器
//配置变更监听器
private static final Emitter . Listener modifyConfig = new Emitter . Listener ( ) {
private static final Emitter . Listener modifyConfig = new Emitter . Listener ( ) {
@Override
@Override
@ -282,7 +349,7 @@ public class DesignerSocketIO {
private static void printLog ( Object [ ] objects , PrintEventLog printEventLog , String prefix ) {
private static void printLog ( Object [ ] objects , PrintEventLog printEventLog , String prefix ) {
for ( Object object : objects ) {
for ( Object object : objects ) {
if ( object instanceof Throwable ) {
if ( object instanceof Throwable ) {
Throwable throwable = ( Throwable ) object ;
Throwable throwable = ( Throwable ) object ;
printEventLog . printThrowable ( throwable ) ;
printEventLog . printThrowable ( throwable ) ;
} else {
} else {
printEventLog . print ( prefix , object ) ;
printEventLog . print ( prefix , object ) ;
@ -292,7 +359,8 @@ public class DesignerSocketIO {
interface PrintEventLog {
interface PrintEventLog {
void printThrowable ( Throwable throwable ) ;
void printThrowable ( Throwable throwable ) ;
void print ( String s , Object . . . object ) ;
void print ( String s , Object . . . object ) ;
}
}
enum PrintEventLogImpl implements PrintEventLog {
enum PrintEventLogImpl implements PrintEventLog {