wavetermdev/waveterm · error

unknown connection type for conn %q: %s

Error message

unknown connection type for conn %q: %s

What it means

Terminal else-branch of the connection-type dispatch in setupAndStartShellProcess: ConnUnion.ConnType was neither ConnType_Wsl, ConnType_Ssh, nor ConnType_Local. This is an internal invariant breach — getConnUnion should only ever produce those three types.

Source

Thrown at pkg/blockcontroller/shellcontroller.go:515

				ProcRoute: true,
				SockName:  sockName,
				BlockId:   bc.BlockId,
			}
			jwtStr, err := wshutil.MakeClientJWTToken(rpcContext)
			if err != nil {
				return nil, fmt.Errorf("error making jwt token: %w", err)
			}
			swapToken.RpcContext = &rpcContext
			swapToken.Env[wshutil.WaveJwtTokenVarName] = jwtStr
		}
		cmdOpts.ShellPath = connUnion.ShellPath
		cmdOpts.ShellOpts = getLocalShellOpts(blockMeta)
		shellProc, err = shellexec.StartLocalShellProc(logCtx, rc.TermSize, cmdStr, cmdOpts, remoteName)
		if err != nil {
			return nil, err
		}
	} else {
		return nil, fmt.Errorf("unknown connection type for conn %q: %s", remoteName, connUnion.ConnType)
	}
	bc.UpdateControllerAndSendUpdate(func() bool {
		bc.ShellProc = shellProc
		bc.ProcStatus = Status_Running
		return true
	})
	return shellProc, nil
}

func (bc *ShellController) manageRunningShellProcess(shellProc *shellexec.ShellProc, rc *RunShellOpts, blockMeta waveobj.MetaMapType) error {
	shellInputCh := make(chan *BlockInputUnion, 32)
	bc.ShellInputCh = shellInputCh

	go func() {
		// handles regular output from the pty (goes to the blockfile and xterm)
		defer func() {
			panichandler.PanicHandler("blockcontroller:shellproc-pty-read-loop", recover())
		}()

View on GitHub (pinned to a4447c1563)

Solutions

  1. Verify remoteName resolves through getConnUnion to a known ConnType before calling setupAndStartShellProcess
  2. Update the dispatch (and getConnUnion) so every new ConnType has a corresponding start branch
  3. Re-create the block/session state if a stale conn type code was restored from disk
  4. File a bug with the logged remoteName and ConnType if this occurs on a stock build

Example fix

// before: adding a new conn type but not the start branch
rtn.ConnType = ConnType_Docker // new type, no handling in setupAndStartShellProcess

// after: handle it or reject early
if connUnion.ConnType != ConnType_Wsl && connUnion.ConnType != ConnType_Ssh && connUnion.ConnType != ConnType_Local {
    return nil, fmt.Errorf("unsupported conn type %s", connUnion.ConnType)
}
Defensive patterns

Strategy: validation

Validate before calling

if connUnion.ConnType != ConnType_Wsl && connUnion.ConnType != ConnType_Ssh && connUnion.ConnType != ConnType_Local {
    return fmt.Errorf("refusing to start shell: invalid conn type %s", connUnion.ConnType)
}

Type guard

func validConnType(t ConnType) bool {
    return t == ConnType_Wsl || t == ConnType_Ssh || t == ConnType_Local
}

Try / catch

proc, err := bc.setupAndStartShellProcess(logCtx, rc, blockMeta)
if err != nil && strings.Contains(err.Error(), "unknown connection type for conn") {
    // re-resolve via getConnUnion or recreate the block
}

Prevention

When it happens

Trigger: A ConnUnion with an unset (zero-value) or foreign ConnType reaches the shell-start dispatch, e.g. after a future/modified getConnUnion adds a new ConnType without updating setupAndStartShellProcess, or a partially-initialized ConnUnion is passed in.

Common situations: Custom/experimental builds extending connection types without updating the shell startup switch; race where ConnUnion zero-value struct is used before getConnUnion populated it; deserialized session state carrying an obsolete conn type code.

Related errors


AI-assisted analysis of wavetermdev/waveterm@a4447c1563 (2026-09-01). Data as JSON: /api/errors/81aae68d6830b7d4. Report an issue: GitHub.