@@ -6,7 +6,6 @@ import com.coder.gateway.cli.CoderCLIManager
66import com.coder.gateway.cli.ensureCLI
77import com.coder.gateway.models.TokenSource
88import com.coder.gateway.models.WorkspaceAndAgentStatus
9- import com.coder.gateway.sdk.BaseCoderRestClient
109import com.coder.gateway.sdk.CoderRestClient
1110import com.coder.gateway.sdk.ex.AuthenticationResponseException
1211import com.coder.gateway.sdk.v2.models.Workspace
@@ -15,12 +14,17 @@ import com.coder.gateway.sdk.v2.models.WorkspaceStatus
1514import com.coder.gateway.services.CoderSettingsService
1615import com.coder.gateway.util.toURL
1716import com.coder.gateway.util.withPath
17+ import com.coder.gateway.views.steps.CoderWorkspaceStepView
18+ import com.coder.gateway.views.steps.CoderWorkspacesStepSelection
19+ import com.intellij.openapi.application.ApplicationManager
1820import com.intellij.openapi.components.service
1921import com.intellij.openapi.diagnostic.Logger
22+ import com.intellij.openapi.ui.DialogWrapper
2023import com.jetbrains.gateway.api.ConnectionRequestor
2124import com.jetbrains.gateway.api.GatewayConnectionHandle
2225import com.jetbrains.gateway.api.GatewayConnectionProvider
2326import java.net.URL
27+ import javax.swing.JComponent
2428
2529// In addition to `type`, these are the keys that we support in our Gateway
2630// links.
@@ -34,6 +38,18 @@ private const val IDE_DOWNLOAD_LINK = "ide_download_link"
3438private const val IDE_PRODUCT_CODE = " ide_product_code"
3539private const val IDE_BUILD_NUMBER = " ide_build_number"
3640private const val IDE_PATH_ON_HOST = " ide_path_on_host"
41+ private const val PROJECT_PATH = " project_path"
42+
43+ class SelectWorkspaceIDEDialog (private val comp : JComponent ) : DialogWrapper(true ) {
44+ init {
45+ init ()
46+ title = " Select workspace IDE"
47+ }
48+
49+ override fun createCenterPanel (): JComponent ? {
50+ return comp
51+ }
52+ }
3753
3854// CoderGatewayConnectionProvider handles connecting via a Gateway link such as
3955// jetbrains-gateway://connect#type=coder.
@@ -93,31 +109,38 @@ class CoderGatewayConnectionProvider : GatewayConnectionProvider {
93109 cli.login(client.token)
94110
95111 indicator.text = " Configuring Coder CLI..."
96- cli.configSsh(client.agentNames(workspaces))
97-
98- // TODO: Ask for these if missing. Maybe we can reuse the second
99- // step of the wizard? Could also be nice if we automatically used
100- // the last IDE.
101- if (parameters[IDE_PRODUCT_CODE ].isNullOrBlank()) {
102- throw IllegalArgumentException (" Query parameter \" $IDE_PRODUCT_CODE \" is missing" )
103- }
104- if (parameters[IDE_BUILD_NUMBER ].isNullOrBlank()) {
105- throw IllegalArgumentException (" Query parameter \" $IDE_BUILD_NUMBER \" is missing" )
106- }
107- if (parameters[IDE_PATH_ON_HOST ].isNullOrBlank() && parameters[IDE_DOWNLOAD_LINK ].isNullOrBlank()) {
108- throw IllegalArgumentException (" One of \" $IDE_PATH_ON_HOST \" or \" $IDE_DOWNLOAD_LINK \" is required" )
109- }
110-
111- // Check that both the domain and the redirected domain are
112- // allowlisted. If not, check with the user whether to proceed.
113- verifyDownloadLink(parameters)
114-
115- // TODO: Ask for the project path if missing and validate the path.
116- val folder = parameters[FOLDER ] ? : throw IllegalArgumentException (" Query parameter \" $FOLDER \" is missing" )
117-
118- parameters
119- .withWorkspaceHostname(CoderCLIManager .getHostName(deploymentURL.toURL(), agent.name))
120- .withProjectPath(folder)
112+ cli.configSsh(client.agentNames(workspaces).toSet())
113+
114+
115+ val openDialog = if (parameters[IDE_PRODUCT_CODE ].isNullOrBlank())
116+ true
117+ else if (parameters[IDE_BUILD_NUMBER ].isNullOrBlank())
118+ true
119+ else if (parameters[IDE_PATH_ON_HOST ].isNullOrBlank() && parameters[IDE_DOWNLOAD_LINK ].isNullOrBlank())
120+ true
121+ else if (parameters[FOLDER ].isNullOrBlank())
122+ true
123+ else
124+ false
125+
126+ val params = if (openDialog) {
127+ val view = CoderWorkspaceStepView {}
128+ ApplicationManager .getApplication().invokeAndWait {
129+ view.init (
130+ CoderWorkspacesStepSelection (agent, workspace, cli, client, workspaces)
131+ )
132+ val dialog = SelectWorkspaceIDEDialog (view.component)
133+ dialog.show()
134+ }
135+ val p = parameters.toMutableMap()
136+ listOf (IDE_PRODUCT_CODE , IDE_BUILD_NUMBER , IDE_DOWNLOAD_LINK , IDE_PATH_ON_HOST , PROJECT_PATH ).forEach { prop ->
137+ view.data()[prop]?.let { value -> p[prop] = value }
138+ }
139+ p
140+ } else
141+ parameters.withProjectPath(parameters[FOLDER ]!! )
142+
143+ params.withWorkspaceHostname(CoderCLIManager .getHostName(deploymentURL.toURL(), " ${workspace.name} .${agent.name} " ))
121144 .withWebTerminalLink(client.url.withPath(" /@$username /$workspace .name/terminal" ).toString())
122145 .withConfigDirectory(cli.coderConfigPath.toString())
123146 .withName(workspaceName)
@@ -129,7 +152,7 @@ class CoderGatewayConnectionProvider : GatewayConnectionProvider {
129152 * Return an authenticated Coder CLI and the user's name, asking for the
130153 * token as long as it continues to result in an authentication failure.
131154 */
132- private fun authenticate (deploymentURL : URL , queryToken : String? , lastToken : Pair <String , TokenSource >? = null): Pair <BaseCoderRestClient , String > {
155+ private fun authenticate (deploymentURL : URL , queryToken : String? , lastToken : Pair <String , TokenSource >? = null): Pair <CoderRestClient , String > {
133156 // Use the token from the query, unless we already tried that.
134157 val isRetry = lastToken != null
135158 val token = if (! queryToken.isNullOrBlank() && ! isRetry)
0 commit comments