Skip to content
This repository was archived by the owner on Aug 30, 2024. It is now read-only.

Commit ba00661

Browse files
committed
Cleanup code
- move resize events to xterminal - only set TERM on ttys Change-Id: Idcec7e782b3fc731742f9c9b436d71a03c1f05c3
1 parent d0eb719 commit ba00661

File tree

5 files changed

+93
-99
lines changed

5 files changed

+93
-99
lines changed

cmd/coder/resize_unix.go

Lines changed: 0 additions & 39 deletions
This file was deleted.

cmd/coder/resize_windows.go

Lines changed: 0 additions & 47 deletions
This file was deleted.

cmd/coder/shell.go

Lines changed: 10 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -36,13 +36,6 @@ type resizeEvent struct {
3636
height, width uint16
3737
}
3838

39-
func (s resizeEvent) equal(s2 *resizeEvent) bool {
40-
if s2 == nil {
41-
return false
42-
}
43-
return s.height == s2.height && s.width == s2.width
44-
}
45-
4639
func (cmd *shellCmd) Run(fl *pflag.FlagSet) {
4740
if len(fl.Args()) < 1 {
4841
exitUsage(fl)
@@ -71,14 +64,14 @@ func (cmd *shellCmd) Run(fl *pflag.FlagSet) {
7164
}
7265

7366
func sendResizeEvents(ctx context.Context, termfd uintptr, process wsep.Process) {
74-
events := resizeEvents(ctx, termfd)
67+
events := xterminal.ResizeEvents(ctx, termfd)
7568

7669
// Limit the frequency of resizes to prevent a stuttering effect.
7770
resizeLimiter := rate.NewLimiter(rate.Every(time.Millisecond*100), 1)
7871
for {
7972
select {
8073
case newsize := <-events:
81-
err := process.Resize(ctx, newsize.height, newsize.width)
74+
err := process.Resize(ctx, newsize.Height, newsize.Width)
8275
if err != nil {
8376
return
8477
}
@@ -121,9 +114,13 @@ func runCommand(ctx context.Context, envName string, command string, args []stri
121114
}
122115
go heartbeat(ctx, conn, 15*time.Second)
123116

124-
term := os.Getenv("TERM")
125-
if term == "" {
126-
term = "xterm" // TODO: fix this
117+
var cmdEnv []string
118+
if tty {
119+
term := os.Getenv("TERM")
120+
if term == "" {
121+
term = "xterm"
122+
}
123+
cmdEnv = append(cmdEnv, "TERM="+term)
127124
}
128125

129126
execer := wsep.RemoteExecer(conn)
@@ -132,7 +129,7 @@ func runCommand(ctx context.Context, envName string, command string, args []stri
132129
Args: args,
133130
TTY: tty,
134131
Stdin: true,
135-
Env: []string{"TERM=" + term},
132+
Env: cmdEnv,
136133
})
137134
if err != nil {
138135
return err

internal/xterminal/terminal.go

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,12 @@
33
package xterminal
44

55
import (
6+
"context"
7+
"os"
8+
"os/signal"
9+
610
"golang.org/x/crypto/ssh/terminal"
11+
"golang.org/x/sys/unix"
712
)
813

914
// State differs per-platform.
@@ -35,3 +40,32 @@ func Restore(fd uintptr, state *State) error {
3540
func ColorEnabled(fd uintptr) (bool, error) {
3641
return terminal.IsTerminal(int(fd)), nil
3742
}
43+
44+
type ResizeEvent struct {
45+
Height, Width uint16
46+
}
47+
48+
// ResizeEvents sends terminal resize events
49+
func ResizeEvents(ctx context.Context, termfd uintptr) chan ResizeEvent {
50+
sigs := make(chan os.Signal, 16)
51+
signal.Notify(sigs, unix.SIGWINCH)
52+
53+
events := make(chan ResizeEvent)
54+
55+
go func() {
56+
for ctx.Err() == nil {
57+
width, height, err := terminal.GetSize(int(termfd))
58+
if err != nil {
59+
return
60+
}
61+
events <- ResizeEvent{
62+
Height: uint16(height),
63+
Width: uint16(width),
64+
}
65+
66+
<-sigs
67+
}
68+
}()
69+
70+
return events
71+
}

internal/xterminal/terminal_windows.go

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,10 @@
33
package xterminal
44

55
import (
6+
"context"
7+
"time"
8+
9+
"golang.org/x/crypto/ssh/terminal"
610
"golang.org/x/sys/windows"
711
)
812

@@ -66,3 +70,48 @@ func ColorEnabled(handle uintptr) (bool, error) {
6670

6771
return st&windows.ENABLE_VIRTUAL_TERMINAL_PROCESSING != 0, nil
6872
}
73+
74+
type ResizeEvent struct {
75+
Height, Width uint16
76+
}
77+
78+
func (s ResizeEvent) equal(s2 *ResizeEvent) bool {
79+
if s2 == nil {
80+
return false
81+
}
82+
return s.Height == s2.Height && s.Width == s2.Width
83+
}
84+
85+
// ResizeEvents sends terminal resize events when the dimensions change.
86+
// Windows does not have a unix.SIGWINCH equivalent, so we poll the terminal size
87+
// at a fixed interval
88+
func ResizeEvents(ctx context.Context, termfd uintptr) chan ResizeEvent {
89+
events := make(chan ResizeEvent)
90+
t := time.Tick(time.Millisecond * 100)
91+
92+
go func() {
93+
var lastEvent *ResizeEvent
94+
95+
for {
96+
select {
97+
case <-ctx.Done():
98+
return
99+
case <-t:
100+
width, height, err := terminal.GetSize(int(windows.Handle(termfd)))
101+
if err != nil {
102+
return
103+
}
104+
event := ResizeEvent{
105+
Height: uint16(height),
106+
Width: uint16(width),
107+
}
108+
if !event.equal(lastEvent) {
109+
events <- event
110+
}
111+
lastEvent = &event
112+
}
113+
}
114+
}()
115+
116+
return events
117+
}

0 commit comments

Comments
 (0)