@@ -7,8 +7,10 @@ import (
77 "errors"
88 "fmt"
99 "net"
10+ "net/http"
1011 "strconv"
1112 "strings"
13+ "time"
1214
1315 "github.com/cli/cli/v2/internal/codespaces"
1416 "github.com/cli/cli/v2/internal/codespaces/api"
@@ -253,6 +255,15 @@ func (a *App) UpdatePortVisibility(ctx context.Context, codespaceName string, ar
253255 for _ , port := range ports {
254256 a .StartProgressIndicatorWithLabel (fmt .Sprintf ("Updating port %d visibility to: %s" , port .number , port .visibility ))
255257 err := session .UpdateSharedServerPrivacy (ctx , port .number , port .visibility )
258+
259+ // wait for succeed or failure
260+ ctx , cancel := context .WithTimeout (ctx , 30 * time .Second )
261+ defer cancel ()
262+
263+ if err := a .waitForPortUpdate (ctx , session , port .number ); err != nil {
264+ return fmt .Errorf ("error waiting for port update: %w" , err )
265+ }
266+
256267 a .StopProgressIndicator ()
257268 if err != nil {
258269 return fmt .Errorf ("error update port to public: %w" , err )
@@ -262,6 +273,48 @@ func (a *App) UpdatePortVisibility(ctx context.Context, codespaceName string, ar
262273 return nil
263274}
264275
276+ type portChangeKind string
277+
278+ const (
279+ portChangeKindUpdate portChangeKind = "update"
280+ )
281+
282+ type portData struct {
283+ Port int `json:"port"`
284+ ChangeKind portChangeKind `json:"changeKind"`
285+ ErrorDetail string `json:"errorDetail"`
286+ StatusCode int `json:"statusCode"`
287+ }
288+
289+ func (a * App ) waitForPortUpdate (ctx context.Context , session * liveshare.Session , port int ) error {
290+ success := session .WaitForEvent ("sharingSucceeded" )
291+ failure := session .WaitForEvent ("sharingFailed" )
292+
293+ for {
294+ select {
295+ case <- ctx .Done ():
296+ return fmt .Errorf ("timeout waiting for server sharing to succeed or fail" )
297+ case b := <- success :
298+ if err := json .Unmarshal (b , & portData ); err != nil {
299+ return fmt .Errorf ("error unmarshaling port data: %w" , err )
300+ }
301+ if portData .Port == port && portData .ChangeKind == portChangeKindUpdate {
302+ return nil
303+ }
304+ case b := <- failure :
305+ if err := json .Unmarshal (b , & portData ); err != nil {
306+ return fmt .Errorf ("error unmarshaling port data: %w" , err )
307+ }
308+ if portData .Port == port && portData .ChangeKind == portChangeKindUpdate {
309+ if portData .StatusCode == http .StatusForbidden {
310+ return errors .New ("organization admin has forbidden this privacy setting" )
311+ }
312+ return errors .New (portData .ErrorDetail )
313+ }
314+ }
315+ }
316+ }
317+
265318type portVisibility struct {
266319 number int
267320 visibility string
0 commit comments