diff options
| author | Emīls Piņķis <emils@mullvad.net> | 2019-06-06 13:44:01 +0100 |
|---|---|---|
| committer | Emīls Piņķis <emils@mullvad.net> | 2019-06-06 13:44:01 +0100 |
| commit | d20fed36f95e2d535b2272777a78dc84ed9e1e6b (patch) | |
| tree | ebc691c10fd67f5b0f63d967afb319aa4288a462 /gui | |
| parent | 9ab06703eba719bafeef9495cd2aa16cfbd13d1e (diff) | |
| parent | 71515c8c71fad734386934a4bb4715c28c97a5f4 (diff) | |
| download | mullvadvpn-d20fed36f95e2d535b2272777a78dc84ed9e1e6b.tar.xz mullvadvpn-d20fed36f95e2d535b2272777a78dc84ed9e1e6b.zip | |
Merge branch 'show-bridge-in-gui'
Diffstat (limited to 'gui')
| -rw-r--r-- | gui/src/main/daemon-rpc.ts | 1 | ||||
| -rw-r--r-- | gui/src/renderer/components/Connect.tsx | 26 | ||||
| -rw-r--r-- | gui/src/renderer/components/ConnectionInfo.tsx | 25 | ||||
| -rw-r--r-- | gui/src/renderer/components/ConnectionInfoDisclosure.tsx | 9 | ||||
| -rw-r--r-- | gui/src/renderer/components/TunnelControl.tsx | 23 | ||||
| -rw-r--r-- | gui/src/renderer/redux/connection/reducers.ts | 2 | ||||
| -rw-r--r-- | gui/src/shared/daemon-rpc-types.ts | 25 | ||||
| -rw-r--r-- | gui/test/components/NotificationArea.spec.tsx | 2 |
8 files changed, 94 insertions, 19 deletions
diff --git a/gui/src/main/daemon-rpc.ts b/gui/src/main/daemon-rpc.ts index 86ef3dff0a..f50428ea8a 100644 --- a/gui/src/main/daemon-rpc.ts +++ b/gui/src/main/daemon-rpc.ts @@ -41,6 +41,7 @@ const locationSchema = maybe( longitude: number, mullvad_exit_ip: boolean, hostname: maybe(string), + bridge_hostname: maybe(string), }), ); diff --git a/gui/src/renderer/components/Connect.tsx b/gui/src/renderer/components/Connect.tsx index dea950b3f1..60fca1df50 100644 --- a/gui/src/renderer/components/Connect.tsx +++ b/gui/src/renderer/components/Connect.tsx @@ -12,7 +12,7 @@ import ImageView from './ImageView'; import { Container, Header, Layout } from './Layout'; import Map, { MarkerStyle, ZoomLevel } from './Map'; import NotificationArea from './NotificationArea'; -import TunnelControl, { IRelayInAddress, IRelayOutAddress } from './TunnelControl'; +import TunnelControl, { IBridgeData, IRelayInAddress, IRelayOutAddress } from './TunnelControl'; interface IProps { connection: IConnectionReduxState; @@ -50,7 +50,7 @@ const styles = { paddingLeft: 24, paddingRight: 24, paddingBottom: 0, - marginTop: 186, + marginTop: 176, }), container: Styles.createViewStyle({ flex: 1, @@ -159,6 +159,11 @@ export default class Connect extends Component<IProps, IState> { ? this.tunnelEndpointToRelayInAddress(status.details) : undefined; + const bridgeData: IBridgeData | undefined = + (status.state === 'connecting' || status.state === 'connected') && status.details + ? this.tunnelEndpointToBridgeData(status.details) + : undefined; + return ( <View style={styles.connect}> <Map style={styles.map} {...this.getMapProps()} /> @@ -178,6 +183,8 @@ export default class Connect extends Component<IProps, IState> { hostname={this.props.connection.hostname} defaultConnectionInfoOpen={this.props.connectionInfoOpen} relayInAddress={relayInAddress} + bridge={bridgeData} + bridgeHostname={this.props.connection.bridgeHostname} relayOutAddress={relayOutAddress} onConnect={this.props.onConnect} onDisconnect={this.props.onDisconnect} @@ -321,6 +328,21 @@ export default class Connect extends Component<IProps, IState> { ip: socketAddr.host, port: socketAddr.port, protocol: tunnelEndpoint.protocol, + tunnelType: tunnelEndpoint.tunnelType, + }; + } + + private tunnelEndpointToBridgeData(endpoint: ITunnelEndpoint): IBridgeData | undefined { + if (!endpoint.proxy) { + return undefined; + } + + const socketAddr = parseSocketAddress(endpoint.proxy.address); + return { + ip: socketAddr.host, + port: socketAddr.port, + protocol: endpoint.proxy.protocol, + bridgeType: endpoint.proxy.proxyType, }; } } diff --git a/gui/src/renderer/components/ConnectionInfo.tsx b/gui/src/renderer/components/ConnectionInfo.tsx index 7ab8d9907f..7bf5f4fed9 100644 --- a/gui/src/renderer/components/ConnectionInfo.tsx +++ b/gui/src/renderer/components/ConnectionInfo.tsx @@ -1,7 +1,9 @@ import * as React from 'react'; import { Component, Styles, Text, Types, View } from 'reactxp'; +import { proxyTypeToString, TunnelType, tunnelTypeToString } from '../../shared/daemon-rpc-types'; import { messages } from '../../shared/gettext'; import { default as ConnectionInfoDisclosure } from './ConnectionInfoDisclosure'; +import { IBridgeData } from './TunnelControl'; const styles = { row: Styles.createViewStyle({ @@ -42,6 +44,7 @@ interface IInAddress { ip: string; port: number; protocol: string; + tunnelType: TunnelType; } interface IOutAddress { @@ -51,7 +54,9 @@ interface IOutAddress { interface IProps { hostname?: string; + bridgeHostname?: string; inAddress?: IInAddress; + bridgeInfo?: IBridgeData; outAddress?: IOutAddress; defaultOpen?: boolean; style?: Types.ViewStyleRuleSet | Types.ViewStyleRuleSet[]; @@ -72,24 +77,34 @@ export default class ConnectionInfo extends Component<IProps, IState> { } public render() { - const { inAddress, outAddress } = this.props; + const { inAddress, outAddress, bridgeInfo } = this.props; + const transportLine = + (inAddress ? tunnelTypeToString(inAddress.tunnelType) : '') + + (bridgeInfo && inAddress ? ' via ' + proxyTypeToString(bridgeInfo.bridgeType) : ''); + + const entryPoint = bridgeInfo && inAddress ? bridgeInfo : inAddress; return ( <View style={this.props.style}> <View style={styles.header}> - <Text style={styles.hostname}>{this.props.hostname || ''}</Text> <ConnectionInfoDisclosure defaultOpen={this.props.defaultOpen} onToggle={this.onToggle}> - {messages.pgettext('connection-info', 'Connection details')} + <Text style={styles.hostname}> + {this.props.hostname || ''}{' '} + {this.props.bridgeHostname ? `via ${this.props.bridgeHostname}` : ''} + </Text> </ConnectionInfoDisclosure> </View> {this.state.isOpen && ( <React.Fragment> - {inAddress && ( + {this.props.inAddress && ( + <View style={styles.row}>{<Text style={styles.value}>{transportLine}</Text>}</View> + )} + {entryPoint && ( <View style={styles.row}> <Text style={styles.caption}>{messages.pgettext('connection-info', 'In')}</Text> <Text style={styles.value}> - {`${inAddress.ip}:${inAddress.port} ${inAddress.protocol.toUpperCase()}`} + {`${entryPoint.ip}:${entryPoint.port} ${entryPoint.protocol.toUpperCase()}`} </Text> </View> )} diff --git a/gui/src/renderer/components/ConnectionInfoDisclosure.tsx b/gui/src/renderer/components/ConnectionInfoDisclosure.tsx index 93cd17b1d0..6dc324e78f 100644 --- a/gui/src/renderer/components/ConnectionInfoDisclosure.tsx +++ b/gui/src/renderer/components/ConnectionInfoDisclosure.tsx @@ -1,5 +1,5 @@ import * as React from 'react'; -import { Component, Styles, Text, Types, View } from 'reactxp'; +import { Component, Styles, Types, View } from 'reactxp'; import ImageView from './ImageView'; const styles = { @@ -23,7 +23,7 @@ const styles = { interface IProps { onToggle?: (isOpen: boolean) => void; defaultOpen?: boolean; - children: string; + children: React.ReactNode; style?: Types.ViewStyleRuleSet | Types.ViewStyleRuleSet[]; } @@ -51,10 +51,7 @@ export default class ConnectionInfoDisclosure extends Component<IProps, IState> onMouseEnter={this.onMouseEnter} onMouseLeave={this.onMouseLeave} onPress={this.onToggle}> - <Text - style={[styles.caption.base, this.state.isHovered ? styles.caption.hovered : undefined]}> - {this.props.children} - </Text> + {this.props.children} <ImageView source={this.state.isOpen ? 'icon-chevron-up' : 'icon-chevron-down'} width={24} diff --git a/gui/src/renderer/components/TunnelControl.tsx b/gui/src/renderer/components/TunnelControl.tsx index ccad62cb51..ed062c9f0d 100644 --- a/gui/src/renderer/components/TunnelControl.tsx +++ b/gui/src/renderer/components/TunnelControl.tsx @@ -1,18 +1,31 @@ import * as React from 'react'; import { Component, Styles, Text, Types, View } from 'reactxp'; import { colors } from '../../config.json'; -import { RelayProtocol, TunnelStateTransition } from '../../shared/daemon-rpc-types'; +import { + ProxyType, + RelayProtocol, + TunnelStateTransition, + TunnelType, +} from '../../shared/daemon-rpc-types'; import { cities, countries, messages, relayLocations } from '../../shared/gettext'; import * as AppButton from './AppButton'; import ConnectionInfo from './ConnectionInfo'; import SecuredLabel, { SecuredDisplayStyle } from './SecuredLabel'; -export interface IRelayInAddress { +export interface IEndpoint { ip: string; port: number; protocol: RelayProtocol; } +export interface IRelayInAddress extends IEndpoint { + tunnelType: TunnelType; +} + +export interface IBridgeData extends IEndpoint { + bridgeType: ProxyType; +} + export interface IRelayOutAddress { ipv4?: string; ipv6?: string; @@ -27,6 +40,8 @@ interface ITunnelControlProps { defaultConnectionInfoOpen?: boolean; relayInAddress?: IRelayInAddress; relayOutAddress?: IRelayOutAddress; + bridge?: IBridgeData; + bridgeHostname?: string; onConnect: () => void; onDisconnect: () => void; onSelectLocation: () => void; @@ -39,7 +54,7 @@ const styles = { paddingLeft: 24, paddingRight: 24, paddingBottom: 0, - marginTop: 186, + marginTop: 176, flex: 1, }), footer: Styles.createViewStyle({ @@ -145,7 +160,9 @@ export default class TunnelControl extends Component<ITunnelControlProps> { const connectionDetails = ( <ConnectionInfo hostname={this.props.hostname} + bridgeHostname={this.props.bridgeHostname} inAddress={this.props.relayInAddress} + bridgeInfo={this.props.bridge} outAddress={this.props.relayOutAddress} defaultOpen={this.props.defaultConnectionInfoOpen} onToggle={this.props.onToggleConnectionInfo} diff --git a/gui/src/renderer/redux/connection/reducers.ts b/gui/src/renderer/redux/connection/reducers.ts index 5175b6c5ec..2719f3d3db 100644 --- a/gui/src/renderer/redux/connection/reducers.ts +++ b/gui/src/renderer/redux/connection/reducers.ts @@ -7,6 +7,7 @@ export interface IConnectionReduxState { ipv4?: Ip; ipv6?: Ip; hostname?: string; + bridgeHostname?: string; latitude?: number; longitude?: number; country?: string; @@ -19,6 +20,7 @@ const initialState: IConnectionReduxState = { ipv4: undefined, ipv6: undefined, hostname: undefined, + bridgeHostname: undefined, latitude: undefined, longitude: undefined, country: undefined, diff --git a/gui/src/shared/daemon-rpc-types.ts b/gui/src/shared/daemon-rpc-types.ts index 3225995e75..891c06c8b9 100644 --- a/gui/src/shared/daemon-rpc-types.ts +++ b/gui/src/shared/daemon-rpc-types.ts @@ -12,6 +12,7 @@ export interface ILocation { longitude: number; mullvadExitIp: boolean; hostname?: string; + bridgeHostname?: string; } export type BlockReason = @@ -32,22 +33,42 @@ export type AfterDisconnect = 'nothing' | 'block' | 'reconnect'; export type TunnelState = 'connecting' | 'connected' | 'disconnecting' | 'disconnected' | 'blocked'; export type TunnelType = 'wireguard' | 'openvpn'; +export function tunnelTypeToString(tunnel: TunnelType): string { + switch (tunnel) { + case 'wireguard': + return 'WireGuard'; + case 'openvpn': + return 'OpenVPN'; + default: + return ''; + } +} export type RelayProtocol = 'tcp' | 'udp'; export type ProxyType = 'shadowsocks' | 'custom'; +export function proxyTypeToString(proxy: ProxyType): string { + switch (proxy) { + case 'shadowsocks': + return 'Shadowsocks'; + case 'custom': + return 'Custom'; + default: + return ''; + } +} export interface ITunnelEndpoint { address: string; protocol: RelayProtocol; - tunnel: TunnelType; + tunnelType: TunnelType; proxy?: IProxyEndpoint; } export interface IProxyEndpoint { address: string; protocol: RelayProtocol; - proxy_type: ProxyType; + proxyType: ProxyType; } export type DaemonEvent = diff --git a/gui/test/components/NotificationArea.spec.tsx b/gui/test/components/NotificationArea.spec.tsx index c117db914e..7b1a69bd8a 100644 --- a/gui/test/components/NotificationArea.spec.tsx +++ b/gui/test/components/NotificationArea.spec.tsx @@ -65,7 +65,7 @@ describe('components/NotificationArea', () => { details: { address: '1.2.3.4', protocol: 'tcp', - tunnel: 'openvpn', + tunnelType: 'openvpn', }, }} version={defaultVersion} |
