@@ -30,6 +30,7 @@ import (
3030
3131const (
3232 workspaceIndex = "workspaceIndex"
33+ ipAddressIndex = "ipAddressIndex"
3334)
3435
3536// getPortStr extracts the port part from a given URL string. Returns "" if parsing fails or port is not specified.
@@ -77,6 +78,15 @@ func NewCRDWorkspaceInfoProvider(client client.Client, scheme *runtime.Scheme) (
7778
7879 return nil , xerrors .Errorf ("object is not a WorkspaceInfo" )
7980 },
81+ ipAddressIndex : func (obj interface {}) ([]string , error ) {
82+ if workspaceInfo , ok := obj .(* common.WorkspaceInfo ); ok {
83+ if workspaceInfo .IPAddress == "" {
84+ return nil , nil
85+ }
86+ return []string {workspaceInfo .IPAddress }, nil
87+ }
88+ return nil , xerrors .Errorf ("object is not a WorkspaceInfo" )
89+ },
8090 }
8191 contextIndexers := cache.Indexers {
8292 workspaceIndex : func (obj interface {}) ([]string , error ) {
@@ -115,12 +125,43 @@ func (r *CRDWorkspaceInfoProvider) WorkspaceInfo(workspaceID string) *common.Wor
115125 return a .StartedAt .After (b .StartedAt )
116126 })
117127
118- return workspaces [0 ].(* common.WorkspaceInfo )
128+ wsInfo := workspaces [0 ].(* common.WorkspaceInfo )
129+
130+ if wsInfo .IPAddress != "" {
131+ wsInfos , err := r .workspacesInfoByIPAddress (wsInfo .IPAddress )
132+ if err != nil {
133+ log .WithError (err ).Error ("error getting workspaces info by IP address" )
134+ return nil
135+ }
136+ if len (wsInfos ) > 1 {
137+ log .Warnf ("multiple workspaces (%d) for IP address %s" , len (wsInfos ), wsInfo .IPAddress )
138+ return nil
139+ }
140+ if len (wsInfos ) == 1 && wsInfos [0 ].WorkspaceID != workspaceID {
141+ log .Warnf ("workspace %s is not the only workspace for IP address %s" , workspaceID , wsInfo .IPAddress )
142+ return nil
143+ }
144+ }
145+ return wsInfo
119146 }
120147
121148 return nil
122149}
123150
151+ func (r * CRDWorkspaceInfoProvider ) workspacesInfoByIPAddress (ipAddress string ) ([]* common.WorkspaceInfo , error ) {
152+ workspaces := make ([]* common.WorkspaceInfo , 0 )
153+
154+ objs , err := r .store .ByIndex (ipAddressIndex , ipAddress )
155+ if err != nil {
156+ return nil , err
157+ }
158+ for _ , w := range objs {
159+ workspaces = append (workspaces , w .(* common.WorkspaceInfo ))
160+ }
161+
162+ return workspaces , nil
163+ }
164+
124165func (r * CRDWorkspaceInfoProvider ) AcquireContext (ctx context.Context , workspaceID string , port string ) (context.Context , string , error ) {
125166 ws := r .WorkspaceInfo (workspaceID )
126167 if ws == nil {
0 commit comments