Commit 2ac180f7 authored by Eric's avatar Eric

new command parse

parent 42917447
package proxy
import (
"bytes"
"fmt"
"github.com/jumpserver/koko/pkg/utils"
"strings"
)
type commandInput struct {
readFromUserInput bytes.Buffer
readFromServerInput bytes.Buffer
isUserSideValid bool
isServerSideValid bool
}
func (c *commandInput) readFromUser(p []byte) {
_, _ = c.readFromUserInput.Write(p)
}
func (c *commandInput) readFromServer(p []byte) {
_, _ = c.readFromServerInput.Write(p)
}
func (c *commandInput) Parse() string {
lines, ok := utils.ParseTerminalData(c.readFromUserInput.Bytes())
if ok {
fmt.Println("readFromUserInput lines: ", lines)
c.readFromUserInput.Reset()
c.readFromServerInput.Reset()
return strings.Join(lines, "\r\n")
}
lines, _ = utils.ParseTerminalData(c.readFromServerInput.Bytes())
fmt.Println("readFromServerInput lines: ", lines)
c.readFromUserInput.Reset()
c.readFromServerInput.Reset()
return strings.Join(lines, "\r\n")
}
type commandOut struct {
readFromServerOut bytes.Buffer
isUserSideValid bool
isServerSideValid bool
}
func (c *commandOut) readFromServer(p []byte) {
_, _ = c.readFromServerOut.Write(p)
}
func (c *commandOut) Parse() string {
lines, _ := utils.ParseTerminalData(c.readFromServerOut.Bytes())
c.readFromServerOut.Reset()
fmt.Println("commandOut: ", lines)
return strings.Join(lines, "\r\n")
}
...@@ -53,10 +53,12 @@ type Parser struct { ...@@ -53,10 +53,12 @@ type Parser struct {
once *sync.Once once *sync.Once
lock *sync.RWMutex lock *sync.RWMutex
command string command string
output string output string
cmdInputParser *CmdParser //cmdInputParser *CmdParser
cmdOutputParser *CmdParser //cmdOutputParser *CmdParser
cmdInputParser *commandInput
cmdOutputParser *commandOut
cmdFilterRules []model.SystemUserFilterRule cmdFilterRules []model.SystemUserFilterRule
closed chan struct{} closed chan struct{}
...@@ -66,9 +68,19 @@ func (p *Parser) initial() { ...@@ -66,9 +68,19 @@ func (p *Parser) initial() {
p.once = new(sync.Once) p.once = new(sync.Once)
p.lock = new(sync.RWMutex) p.lock = new(sync.RWMutex)
p.cmdInputParser = NewCmdParser(p.id, CommandInputParserName) //p.cmdInputParser = NewCmdParser(p.id, CommandInputParserName)
p.cmdOutputParser = NewCmdParser(p.id, CommandOutputParserName) //p.cmdOutputParser = NewCmdParser(p.id, CommandOutputParserName)
p.cmdInputParser = &commandInput{
readFromUserInput: bytes.Buffer{},
readFromServerInput: bytes.Buffer{},
isUserSideValid: false,
isServerSideValid: false,
}
p.cmdOutputParser = &commandOut{
readFromServerOut: bytes.Buffer{},
isUserSideValid: false,
isServerSideValid: false,
}
p.closed = make(chan struct{}) p.closed = make(chan struct{})
p.cmdRecordChan = make(chan [2]string, 1024) p.cmdRecordChan = make(chan [2]string, 1024)
} }
...@@ -86,8 +98,8 @@ func (p *Parser) ParseStream(userInChan, srvInChan <-chan []byte) (userOut, srvO ...@@ -86,8 +98,8 @@ func (p *Parser) ParseStream(userInChan, srvInChan <-chan []byte) (userOut, srvO
close(p.cmdRecordChan) close(p.cmdRecordChan)
close(p.userOutputChan) close(p.userOutputChan)
close(p.srvOutputChan) close(p.srvOutputChan)
_ = p.cmdOutputParser.Close() //_ = p.cmdOutputParser.Close()
_ = p.cmdInputParser.Close() //_ = p.cmdInputParser.Close()
logger.Infof("Session %s: Parser routine done", p.id) logger.Infof("Session %s: Parser routine done", p.id)
}() }()
for { for {
...@@ -120,6 +132,9 @@ func (p *Parser) parseInputState(b []byte) []byte { ...@@ -120,6 +132,9 @@ func (p *Parser) parseInputState(b []byte) []byte {
return b return b
} }
p.inputPreState = p.inputState p.inputPreState = p.inputState
p.cmdInputParser.readFromUser(b)
if bytes.Contains(b, charEnter) { if bytes.Contains(b, charEnter) {
// 连续输入enter key, 结算上一条可能存在的命令结果 // 连续输入enter key, 结算上一条可能存在的命令结果
p.sendCommandRecord() p.sendCommandRecord()
...@@ -128,7 +143,8 @@ func (p *Parser) parseInputState(b []byte) []byte { ...@@ -128,7 +143,8 @@ func (p *Parser) parseInputState(b []byte) []byte {
p.parseCmdInput() p.parseCmdInput()
if cmd, ok := p.IsCommandForbidden(); !ok { if cmd, ok := p.IsCommandForbidden(); !ok {
fbdMsg := utils.WrapperWarn(fmt.Sprintf(i18n.T("Command `%s` is forbidden"), cmd)) fbdMsg := utils.WrapperWarn(fmt.Sprintf(i18n.T("Command `%s` is forbidden"), cmd))
p.cmdOutputParser.WriteData([]byte(fbdMsg)) //p.cmdOutputParser.WriteData([]byte(fbdMsg))
//p.cmdOutputParser.readFromServer([]byte(fbdMsg))
p.srvOutputChan <- []byte("\r\n" + fbdMsg) p.srvOutputChan <- []byte("\r\n" + fbdMsg)
p.cmdRecordChan <- [2]string{p.command, fbdMsg} p.cmdRecordChan <- [2]string{p.command, fbdMsg}
p.command = "" p.command = ""
...@@ -211,10 +227,12 @@ func (p *Parser) splitCmdStream(b []byte) { ...@@ -211,10 +227,12 @@ func (p *Parser) splitCmdStream(b []byte) {
return return
} }
if p.inputState { if p.inputState {
p.cmdInputParser.WriteData(b) //p.cmdInputParser.WriteData(b)
p.cmdInputParser.readFromServer(b)
return return
} }
p.cmdOutputParser.WriteData(b) //p.cmdOutputParser.WriteData(b)
p.cmdOutputParser.readFromServer(b)
} }
// ParseServerOutput 解析服务器输出 // ParseServerOutput 解析服务器输出
......
...@@ -6,9 +6,10 @@ import ( ...@@ -6,9 +6,10 @@ import (
"unicode/utf8" "unicode/utf8"
) )
func ParseTerminalData(p []byte) (lines []string) { func ParseTerminalData(p []byte) (lines []string, ok bool) {
c := bytes.NewReader(p) c := bytes.NewReader(p)
pasteActive := false pasteActive := false
ok = true
var line []rune var line []rune
var pos int var pos int
var remainder []byte var remainder []byte
...@@ -69,9 +70,11 @@ func ParseTerminalData(p []byte) (lines []string) { ...@@ -69,9 +70,11 @@ func ParseTerminalData(p []byte) (lines []string) {
case keyUp: case keyUp:
line = []rune{} line = []rune{}
pos = 0 pos = 0
ok = false
case keyDown: case keyDown:
line = []rune{} line = []rune{}
pos = 0 pos = 0
ok = false
case keyEnter: case keyEnter:
lines = append(lines, string(line)) lines = append(lines, string(line))
line = line[:0] line = line[:0]
...@@ -96,6 +99,7 @@ func ParseTerminalData(p []byte) (lines []string) { ...@@ -96,6 +99,7 @@ func ParseTerminalData(p []byte) (lines []string) {
default: default:
if !isPrintable(key) { if !isPrintable(key) {
fmt.Println("could not printable: ", []byte(string(key)), " ", key) fmt.Println("could not printable: ", []byte(string(key)), " ", key)
ok = false
continue continue
} }
line, pos = AddKeyToLine(key, pos, line) line, pos = AddKeyToLine(key, pos, line)
...@@ -191,4 +195,4 @@ func AddKeyToLine(key rune, pos int, line []rune) ([]rune, int) { ...@@ -191,4 +195,4 @@ func AddKeyToLine(key rune, pos int, line []rune) ([]rune, int) {
line[pos] = key line[pos] = key
pos++ pos++
return line, pos return line, pos
} }
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment