Merge attribute handling from request and response to commen code.
This commit was merged in pull request #7.
This commit is contained in:
59
packages/ipp/boolean.go
Normal file
59
packages/ipp/boolean.go
Normal file
@@ -0,0 +1,59 @@
|
|||||||
|
package ipp
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"encoding/binary"
|
||||||
|
"fmt"
|
||||||
|
"io"
|
||||||
|
|
||||||
|
log "github.com/sirupsen/logrus"
|
||||||
|
)
|
||||||
|
|
||||||
|
type boolean struct {
|
||||||
|
name string
|
||||||
|
value bool
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewBoolean(name string, value bool) *boolean {
|
||||||
|
b := new(boolean)
|
||||||
|
b.name = name
|
||||||
|
b.value = value
|
||||||
|
return b
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b boolean) Name() string {
|
||||||
|
return b.name
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b boolean) String() string {
|
||||||
|
return b.name + ":" + fmt.Sprint(b.value)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *boolean) valueTag() tag {
|
||||||
|
return booleanValueTag
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *boolean) unmarshal(byteStream io.Reader) {
|
||||||
|
log.Warn("Unmarshal of boolean is not implemented yet")
|
||||||
|
}
|
||||||
|
|
||||||
|
func (e *boolean) marshal() []byte {
|
||||||
|
l := 5 + len(e.name)
|
||||||
|
b := make([]byte, 0, l)
|
||||||
|
buf := bytes.NewBuffer(b)
|
||||||
|
buf.WriteByte(byte(booleanValueTag))
|
||||||
|
binary.Write(buf, binary.BigEndian, uint16(len(e.name)))
|
||||||
|
buf.WriteString(e.name)
|
||||||
|
binary.Write(buf, binary.BigEndian, uint16(1))
|
||||||
|
if e.value {
|
||||||
|
buf.WriteByte(byte(1))
|
||||||
|
} else {
|
||||||
|
buf.WriteByte(byte(0))
|
||||||
|
}
|
||||||
|
return buf.Bytes()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (e *boolean) size() int {
|
||||||
|
l := 5 + len(e.name)
|
||||||
|
return l
|
||||||
|
}
|
||||||
@@ -16,9 +16,14 @@ func NewCharSetValue(name string, value string) *charSetValue {
|
|||||||
return c
|
return c
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (c charSetValue) Name() string {
|
||||||
|
return c.name
|
||||||
|
}
|
||||||
|
|
||||||
func (c charSetValue) String() string {
|
func (c charSetValue) String() string {
|
||||||
return c.name + ":" + c.value
|
return c.name + ":" + c.value
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *charSetValue) valueTag() tag {
|
func (c *charSetValue) valueTag() tag {
|
||||||
return charsetValueTag
|
return charsetValueTag
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -21,9 +21,14 @@ func NewEnum(name string, value int32) *enum {
|
|||||||
return e
|
return e
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (e enum) Name() string {
|
||||||
|
return e.name
|
||||||
|
}
|
||||||
|
|
||||||
func (e enum) String() string {
|
func (e enum) String() string {
|
||||||
return e.name + ":" + fmt.Sprint(e.value)
|
return e.name + ":" + fmt.Sprint(e.value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *enum) valueTag() tag {
|
func (e *enum) valueTag() tag {
|
||||||
return enumValueTag
|
return enumValueTag
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,6 +11,10 @@ func NewKeyWord(name string, values ...string) *keyWord {
|
|||||||
return k
|
return k
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (k keyWord) Name() string {
|
||||||
|
return k.sos.name
|
||||||
|
}
|
||||||
|
|
||||||
func (k keyWord) String() string {
|
func (k keyWord) String() string {
|
||||||
return k.sos.String()
|
return k.sos.String()
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ import (
|
|||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
|
|
||||||
|
log "github.com/sirupsen/logrus"
|
||||||
)
|
)
|
||||||
|
|
||||||
// References
|
// References
|
||||||
@@ -121,3 +123,130 @@ func marshalNameValue(name, value string, b []byte) {
|
|||||||
p += 2
|
p += 2
|
||||||
copy(b[p:], []byte(value))
|
copy(b[p:], []byte(value))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type Attribute interface {
|
||||||
|
Name() string
|
||||||
|
valueTag() tag
|
||||||
|
marshal() []byte
|
||||||
|
//size() int
|
||||||
|
}
|
||||||
|
|
||||||
|
type attributes struct {
|
||||||
|
operation []Attribute
|
||||||
|
printer []Attribute
|
||||||
|
job []Attribute
|
||||||
|
}
|
||||||
|
|
||||||
|
func (a *attributes) String() string{
|
||||||
|
s := " OperationAttributes" + "\n"
|
||||||
|
for _, a := range a.operation {
|
||||||
|
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
||||||
|
}
|
||||||
|
s = s + " PrinterAttributes" + "\n"
|
||||||
|
for _, a := range a.printer {
|
||||||
|
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
||||||
|
}
|
||||||
|
s = s + " JobAttributes" + "\n"
|
||||||
|
for _, a := range a.job {
|
||||||
|
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
||||||
|
}
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func (as *attributes) addAttribute(group tag, a Attribute) {
|
||||||
|
switch group {
|
||||||
|
case operationAttributes:
|
||||||
|
as.operation = append(as.operation, a)
|
||||||
|
case jobAttributes:
|
||||||
|
as.job = append(as.job, a)
|
||||||
|
case printerAttributes:
|
||||||
|
as.printer = append(as.printer, a)
|
||||||
|
default:
|
||||||
|
log.Error("Unknown attribute group")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func UnMarshalAttributues(body io.Reader) *attributes {
|
||||||
|
a := new(attributes)
|
||||||
|
|
||||||
|
var t tag
|
||||||
|
err := binary.Read(body, binary.BigEndian, &t)
|
||||||
|
if err != nil {
|
||||||
|
log.Error(err.Error())
|
||||||
|
}
|
||||||
|
log.Debugf("got tag - %v", t)
|
||||||
|
if t != operationAttributes && t != jobAttributes && t != printerAttributes {
|
||||||
|
log.Errorf("Unknown attribute group tag %v", t)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
currentAttributeGroup := t
|
||||||
|
|
||||||
|
var lastAddValuer AddValuer
|
||||||
|
for {
|
||||||
|
err = binary.Read(body, binary.BigEndian, &t)
|
||||||
|
if err != nil {
|
||||||
|
log.Errorf("End of input before end of attributes tag (%v)", err.Error())
|
||||||
|
}
|
||||||
|
log.Debugf("Value tag - %v", t)
|
||||||
|
switch t {
|
||||||
|
case endOfAttributes:
|
||||||
|
return a
|
||||||
|
case charsetValueTag:
|
||||||
|
c := NewCharSetValue("", "")
|
||||||
|
c.unmarshal(body)
|
||||||
|
a.addAttribute(currentAttributeGroup, c)
|
||||||
|
log.Debugf("%v %v", c.name, c.value)
|
||||||
|
case uriValueTag:
|
||||||
|
u := NewUriValue("", "")
|
||||||
|
u.unmarshal(body)
|
||||||
|
a.addAttribute(currentAttributeGroup, u)
|
||||||
|
log.Debugf("%v %v", u.name, u.value)
|
||||||
|
case naturalLanguageValueTag:
|
||||||
|
n := NewNaturalLanguage("", "")
|
||||||
|
n.unmarshal(body)
|
||||||
|
a.addAttribute(currentAttributeGroup, n)
|
||||||
|
log.Debugf("%v %v", n.name, n.value)
|
||||||
|
case keyWordValueTag:
|
||||||
|
name, value := unmarshalSingleValue(body)
|
||||||
|
if name == "" {
|
||||||
|
lastAddValuer.addValue(value)
|
||||||
|
} else {
|
||||||
|
k := NewKeyWord(name, value)
|
||||||
|
a.addAttribute(currentAttributeGroup, k)
|
||||||
|
lastAddValuer = k
|
||||||
|
}
|
||||||
|
log.Debugf("%v : %v", name, value)
|
||||||
|
case nameWithoutLanguageValueTag:
|
||||||
|
n := NewNameWithoutLanguage("", "")
|
||||||
|
n.unmarshal(body)
|
||||||
|
a.addAttribute(currentAttributeGroup, n)
|
||||||
|
log.Debugf("%v %v", n.name, n.value)
|
||||||
|
case mimeMediaTypeValueTag:
|
||||||
|
name, value := unmarshalSingleValue(body)
|
||||||
|
if name == "" {
|
||||||
|
lastAddValuer.addValue(value)
|
||||||
|
} else {
|
||||||
|
m := NewMimeMediaType(name, value)
|
||||||
|
a.addAttribute(currentAttributeGroup, m)
|
||||||
|
lastAddValuer = m
|
||||||
|
}
|
||||||
|
log.Debugf("%v : %v", name, value)
|
||||||
|
case jobAttributes:
|
||||||
|
log.Debug("Start job attributes")
|
||||||
|
currentAttributeGroup = jobAttributes
|
||||||
|
case printerAttributes:
|
||||||
|
log.Debug("Start printer attributes")
|
||||||
|
currentAttributeGroup = printerAttributes
|
||||||
|
case operationAttributes:
|
||||||
|
log.Debug("Start operation attributes")
|
||||||
|
currentAttributeGroup = operationAttributes
|
||||||
|
case resolutionValueTag:
|
||||||
|
res := NewResolution("", 0, 0)
|
||||||
|
res.unmarshal(body)
|
||||||
|
a.addAttribute(currentAttributeGroup, res)
|
||||||
|
log.Debugf("Resolution %v", res)
|
||||||
|
default:
|
||||||
|
log.Errorf("Unsupported tag %v", t)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -11,6 +11,10 @@ func NewMimeMediaType(name string, values ...string) *mimeMediaType {
|
|||||||
return m
|
return m
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (m mimeMediaType) Name() string {
|
||||||
|
return m.sos.name
|
||||||
|
}
|
||||||
|
|
||||||
func (m mimeMediaType) String() string {
|
func (m mimeMediaType) String() string {
|
||||||
return m.sos.String()
|
return m.sos.String()
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -14,6 +14,10 @@ func NewNameWithoutLanguage(name, value string) *NameWithoutLanguage {
|
|||||||
return c
|
return c
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (c NameWithoutLanguage) Name() string {
|
||||||
|
return c.name
|
||||||
|
}
|
||||||
|
|
||||||
func (c NameWithoutLanguage) String() string {
|
func (c NameWithoutLanguage) String() string {
|
||||||
return c.name + ":" + c.value
|
return c.name + ":" + c.value
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,9 +16,14 @@ func NewNaturalLanguage(name, value string) *naturalLanguage {
|
|||||||
return c
|
return c
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (c naturalLanguage) Name() string {
|
||||||
|
return c.name
|
||||||
|
}
|
||||||
|
|
||||||
func (c naturalLanguage) String() string {
|
func (c naturalLanguage) String() string {
|
||||||
return c.name + ":" + c.value
|
return c.name + ":" + c.value
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *naturalLanguage) valueTag() tag {
|
func (c *naturalLanguage) valueTag() tag {
|
||||||
return naturalLanguageValueTag
|
return naturalLanguageValueTag
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,23 +5,21 @@ import (
|
|||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
|
|
||||||
log "github.com/sirupsen/logrus"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type ippRequestHeader struct {
|
type ippMessageHeader struct {
|
||||||
versionNumber versionNumber
|
versionNumber versionNumber
|
||||||
operationId OperationId
|
operationId OperationId
|
||||||
requestId uint32
|
requestId uint32
|
||||||
}
|
}
|
||||||
|
|
||||||
func (h *ippRequestHeader) unmarshal(byteStream io.Reader) {
|
func (h *ippMessageHeader) unmarshal(byteStream io.Reader) {
|
||||||
binary.Read(byteStream, binary.BigEndian, &h.versionNumber)
|
binary.Read(byteStream, binary.BigEndian, &h.versionNumber)
|
||||||
binary.Read(byteStream, binary.BigEndian, &h.operationId)
|
binary.Read(byteStream, binary.BigEndian, &h.operationId)
|
||||||
binary.Read(byteStream, binary.BigEndian, &h.requestId)
|
binary.Read(byteStream, binary.BigEndian, &h.requestId)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (h *ippRequestHeader) marshal() []byte {
|
func (h *ippMessageHeader) marshal() []byte {
|
||||||
b := make([]byte, 0, 8)
|
b := make([]byte, 0, 8)
|
||||||
buf := bytes.NewBuffer(b)
|
buf := bytes.NewBuffer(b)
|
||||||
binary.Write(buf, binary.BigEndian, h.versionNumber)
|
binary.Write(buf, binary.BigEndian, h.versionNumber)
|
||||||
@@ -30,25 +28,17 @@ func (h *ippRequestHeader) marshal() []byte {
|
|||||||
return buf.Bytes()
|
return buf.Bytes()
|
||||||
}
|
}
|
||||||
|
|
||||||
func (h ippRequestHeader) String() string {
|
func (h ippMessageHeader) String() string {
|
||||||
return fmt.Sprintf("Version number: %v Operation Id: %v Request Id: %v", h.versionNumber, h.operationId, h.requestId)
|
return fmt.Sprintf("Version number: %v Operation Id: %v Request Id: %v", h.versionNumber, h.operationId, h.requestId)
|
||||||
}
|
}
|
||||||
|
|
||||||
type Attribute interface {
|
|
||||||
valueTag() tag
|
|
||||||
marshal() []byte
|
|
||||||
//size() int
|
|
||||||
}
|
|
||||||
|
|
||||||
type AddValuer interface {
|
type AddValuer interface {
|
||||||
addValue(string)
|
addValue(string)
|
||||||
}
|
}
|
||||||
|
|
||||||
type Request struct {
|
type Request struct {
|
||||||
operationAttributes map[string]Attribute
|
a *attributes
|
||||||
jobAttributes map[string]Attribute
|
header ippMessageHeader
|
||||||
printerAttributes map[string]Attribute
|
|
||||||
header ippRequestHeader
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewRequest(op OperationId, requestId uint32) *Request {
|
func NewRequest(op OperationId, requestId uint32) *Request {
|
||||||
@@ -56,112 +46,18 @@ func NewRequest(op OperationId, requestId uint32) *Request {
|
|||||||
r.header.operationId = op
|
r.header.operationId = op
|
||||||
r.header.requestId = requestId
|
r.header.requestId = requestId
|
||||||
r.header.versionNumber = 0x0200
|
r.header.versionNumber = 0x0200
|
||||||
r.operationAttributes = make(map[string]Attribute)
|
r.a = new(attributes)
|
||||||
r.jobAttributes = make(map[string]Attribute)
|
|
||||||
r.printerAttributes = make(map[string]Attribute)
|
|
||||||
|
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r Request) String() string {
|
func (r Request) String() string {
|
||||||
s := r.header.String() + "\n" + " OperationAttributes" + "\n"
|
return r.header.String() + "\n" + r.a.String()
|
||||||
for _, a := range r.operationAttributes {
|
|
||||||
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
|
||||||
}
|
|
||||||
s = s + " PrinterAttributes" + "\n"
|
|
||||||
for _, a := range r.printerAttributes {
|
|
||||||
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
|
||||||
}
|
|
||||||
s = s + " JobAttributes" + "\n"
|
|
||||||
for _, a := range r.jobAttributes {
|
|
||||||
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
|
||||||
}
|
|
||||||
return s
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *Request) UnMarshal(body io.Reader) {
|
func (r *Request) UnMarshal(body io.Reader) {
|
||||||
r.header.unmarshal(body)
|
r.header.unmarshal(body)
|
||||||
log.Debugf("Header %v", r.header)
|
//log.Printf("Header %v", r.header)
|
||||||
var tag tag
|
r.a = UnMarshalAttributues(body)
|
||||||
err := binary.Read(body, binary.BigEndian, &tag)
|
|
||||||
if err != nil {
|
|
||||||
log.Error(err.Error())
|
|
||||||
}
|
|
||||||
log.Debugf("got tag - %v", tag)
|
|
||||||
var currentAttributeGroup map[string]Attribute
|
|
||||||
switch tag {
|
|
||||||
case operationAttributes:
|
|
||||||
currentAttributeGroup = r.operationAttributes
|
|
||||||
case jobAttributes:
|
|
||||||
currentAttributeGroup = r.jobAttributes
|
|
||||||
case printerAttributes:
|
|
||||||
currentAttributeGroup = r.printerAttributes
|
|
||||||
default:
|
|
||||||
log.Errorf("Unknown tag %v", tag)
|
|
||||||
}
|
|
||||||
|
|
||||||
var lastAddValuer AddValuer
|
|
||||||
for {
|
|
||||||
err = binary.Read(body, binary.BigEndian, &tag)
|
|
||||||
if err != nil {
|
|
||||||
log.Errorf("End of input before end of attributes tag (%v)", err.Error())
|
|
||||||
}
|
|
||||||
log.Debugf("Value tag - %v", tag)
|
|
||||||
switch tag {
|
|
||||||
case endOfAttributes:
|
|
||||||
return
|
|
||||||
case charsetValueTag:
|
|
||||||
c := NewCharSetValue("", "")
|
|
||||||
c.unmarshal(body)
|
|
||||||
currentAttributeGroup[c.name] = c
|
|
||||||
log.Debugf("%v %v", c.name, c.value)
|
|
||||||
case uriValueTag:
|
|
||||||
u := NewUriValue("", "")
|
|
||||||
u.unmarshal(body)
|
|
||||||
currentAttributeGroup[u.name] = u
|
|
||||||
log.Debugf("%v %v", u.name, u.value)
|
|
||||||
case naturalLanguageValueTag:
|
|
||||||
n := NewNaturalLanguage("", "")
|
|
||||||
n.unmarshal(body)
|
|
||||||
currentAttributeGroup[n.name] = n
|
|
||||||
log.Debugf("%v %v", n.name, n.value)
|
|
||||||
case keyWordValueTag:
|
|
||||||
name, value := unmarshalSingleValue(body)
|
|
||||||
if name == "" {
|
|
||||||
lastAddValuer.addValue(value)
|
|
||||||
} else {
|
|
||||||
k := NewKeyWord(name, value)
|
|
||||||
currentAttributeGroup[name] = k
|
|
||||||
lastAddValuer = k
|
|
||||||
}
|
|
||||||
log.Debugf("%v : %v", name, value)
|
|
||||||
case nameWithoutLanguageValueTag:
|
|
||||||
n := NewNameWithoutLanguage("", "")
|
|
||||||
n.unmarshal(body)
|
|
||||||
currentAttributeGroup[n.name] = n
|
|
||||||
log.Debugf("%v %v", n.name, n.value)
|
|
||||||
case mimeMediaTypeValueTag:
|
|
||||||
name, value := unmarshalSingleValue(body)
|
|
||||||
if name == "" {
|
|
||||||
lastAddValuer.addValue(value)
|
|
||||||
} else {
|
|
||||||
m := NewMimeMediaType(name, value)
|
|
||||||
currentAttributeGroup[name] = m
|
|
||||||
lastAddValuer = m
|
|
||||||
}
|
|
||||||
log.Debugf("%v : %v", name, value)
|
|
||||||
case jobAttributes:
|
|
||||||
log.Debug("Start job attributes")
|
|
||||||
currentAttributeGroup = r.jobAttributes
|
|
||||||
case resolutionValueTag:
|
|
||||||
res := NewResolution("", 0, 0)
|
|
||||||
res.unmarshal(body)
|
|
||||||
currentAttributeGroup[res.name] = res
|
|
||||||
log.Debugf("Resolution %v", res)
|
|
||||||
default:
|
|
||||||
log.Errorf("Unsupported tag %v", tag)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *Request) RequestId() uint32 {
|
func (r *Request) RequestId() uint32 {
|
||||||
@@ -173,31 +69,48 @@ func (r *Request) Operation() OperationId {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (r *Request) GetAttribute(name string) Attribute {
|
func (r *Request) GetAttribute(name string) Attribute {
|
||||||
return r.operationAttributes[name]
|
for _, a := range r.a.operation {
|
||||||
|
if a.Name() == name {
|
||||||
|
return a
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *Request) Marshal() []byte {
|
func (r *Request) Marshal() []byte {
|
||||||
// //s = r.size
|
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
buf.Write(r.header.marshal())
|
buf.Write(r.header.marshal())
|
||||||
if len(r.operationAttributes) > 0 {
|
if len(r.a.operation) > 0 {
|
||||||
buf.WriteByte(byte(operationAttributes))
|
buf.WriteByte(byte(operationAttributes))
|
||||||
for _, e := range r.operationAttributes {
|
for _, e := range r.a.operation {
|
||||||
buf.Write(e.marshal())
|
buf.Write(e.marshal())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if len(r.jobAttributes) > 0 {
|
if len(r.a.job) > 0 {
|
||||||
buf.WriteByte(byte(jobAttributes))
|
buf.WriteByte(byte(jobAttributes))
|
||||||
for _, e := range r.jobAttributes {
|
for _, e := range r.a.job {
|
||||||
buf.Write(e.marshal())
|
buf.Write(e.marshal())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if len(r.printerAttributes) > 0 {
|
if len(r.a.printer) > 0 {
|
||||||
buf.WriteByte(byte(printerAttributes))
|
buf.WriteByte(byte(printerAttributes))
|
||||||
for _, e := range r.printerAttributes {
|
for _, e := range r.a.printer {
|
||||||
buf.Write(e.marshal())
|
buf.Write(e.marshal())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
buf.WriteByte(byte(endOfAttributes))
|
buf.WriteByte(byte(endOfAttributes))
|
||||||
return buf.Bytes()
|
return buf.Bytes()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (r *Request) AddPrinterAttribute(a Attribute) {
|
||||||
|
r.a.addAttribute(printerAttributes, a)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Request) AddOperatonAttribute(a Attribute) {
|
||||||
|
r.a.addAttribute(operationAttributes, a)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Request) AddJobAttribute(a Attribute) {
|
||||||
|
r.a.addAttribute(jobAttributes, a)
|
||||||
|
}
|
||||||
|
|||||||
@@ -66,8 +66,8 @@ func TestUnmarshalRequestPrinterAttributes(T *testing.T) {
|
|||||||
assert.Equal(T, versionNumber(0x0101), req.header.versionNumber, "Wrong version number")
|
assert.Equal(T, versionNumber(0x0101), req.header.versionNumber, "Wrong version number")
|
||||||
assert.Equal(T, GetPrinterAttributes, req.header.operationId, "Wrong Operation")
|
assert.Equal(T, GetPrinterAttributes, req.header.operationId, "Wrong Operation")
|
||||||
assert.Equal(T, uint32(17), req.header.requestId, "Wrong request id")
|
assert.Equal(T, uint32(17), req.header.requestId, "Wrong request id")
|
||||||
assert.Len(T, req.operationAttributes, 4)
|
assert.Len(T, req.a.operation, 4)
|
||||||
v := req.operationAttributes["requested-attributes"].(*keyWord).sos.values
|
v := req.GetAttribute("requested-attributes").(*keyWord).sos.values
|
||||||
assert.Len(T, v, 7)
|
assert.Len(T, v, 7)
|
||||||
assert.Contains(T, v, "printer-make-and-model")
|
assert.Contains(T, v, "printer-make-and-model")
|
||||||
assert.Contains(T, v, "ipp-versions-supported")
|
assert.Contains(T, v, "ipp-versions-supported")
|
||||||
|
|||||||
@@ -40,6 +40,10 @@ func (r *resolution) unmarshal(byteStream io.Reader) {
|
|||||||
binary.Read(byteStream, binary.BigEndian, &r.units)
|
binary.Read(byteStream, binary.BigEndian, &r.units)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (r resolution) Name() string {
|
||||||
|
return r.name
|
||||||
|
}
|
||||||
|
|
||||||
func (r resolution) String() string {
|
func (r resolution) String() string {
|
||||||
return fmt.Sprintf("%v:%v,%v,%v", r.name, r.crossFeedResolution, r.feedResolution, r.units)
|
return fmt.Sprintf("%v:%v,%v,%v", r.name, r.crossFeedResolution, r.feedResolution, r.units)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ package ipp
|
|||||||
import (
|
import (
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"io"
|
||||||
)
|
)
|
||||||
|
|
||||||
type ippResponseHeader struct {
|
type ippResponseHeader struct {
|
||||||
@@ -24,92 +25,69 @@ func (h *ippResponseHeader) marshal() []byte {
|
|||||||
return a
|
return a
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (h *ippResponseHeader) unmarshal(byteStream io.Reader) {
|
||||||
|
binary.Read(byteStream, binary.BigEndian, &h.versionNumber)
|
||||||
|
binary.Read(byteStream, binary.BigEndian, &h.statusCode)
|
||||||
|
binary.Read(byteStream, binary.BigEndian, &h.requestId)
|
||||||
|
}
|
||||||
|
|
||||||
type Response struct {
|
type Response struct {
|
||||||
operationAttributes []Attribute
|
a *attributes
|
||||||
jobAttributes []Attribute
|
header ippResponseHeader
|
||||||
printerAttributes []Attribute
|
|
||||||
header ippResponseHeader
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewResponse(code statusCode, requestId uint32) *Response {
|
func NewResponse(code statusCode, requestId uint32) *Response {
|
||||||
r := new(Response)
|
r := new(Response)
|
||||||
|
r.a = new(attributes)
|
||||||
r.header.versionNumber = 0x0101
|
r.header.versionNumber = 0x0101
|
||||||
r.header.requestId = requestId
|
r.header.requestId = requestId
|
||||||
r.header.statusCode = code
|
r.header.statusCode = code
|
||||||
r.operationAttributes = make([]Attribute, 0)
|
|
||||||
r.printerAttributes = make([]Attribute, 0)
|
|
||||||
r.jobAttributes = make([]Attribute, 0)
|
|
||||||
return r
|
return r
|
||||||
}
|
}
|
||||||
|
|
||||||
// func (r *Response) length() int {
|
|
||||||
// l := 8 + 1
|
|
||||||
// if len(r.jobAttributes) > 0 {
|
|
||||||
// l += 1 //
|
|
||||||
// for _, e := range r.jobAttributes {
|
|
||||||
// l += e.length()
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// for _, e := range r.operationAttributes {
|
|
||||||
// l += e.length()
|
|
||||||
// }
|
|
||||||
// for _, e := range r.printerAttributes {
|
|
||||||
// l += e.length()
|
|
||||||
// }
|
|
||||||
|
|
||||||
// }
|
|
||||||
|
|
||||||
func (r Response) String() string {
|
func (r Response) String() string {
|
||||||
|
return r.header.String() + "\n" + r.a.String()
|
||||||
s := r.header.String() + "\n" + " OperationAttributes" + "\n"
|
|
||||||
for _, a := range r.operationAttributes {
|
|
||||||
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
|
||||||
}
|
|
||||||
s = s + " PrinterAttributes" + "\n"
|
|
||||||
for _, a := range r.printerAttributes {
|
|
||||||
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
|
||||||
}
|
|
||||||
s = s + " JobAttributes" + "\n"
|
|
||||||
for _, a := range r.jobAttributes {
|
|
||||||
s = s + fmt.Sprintf(" %v (%v)\n", a, a.valueTag())
|
|
||||||
}
|
|
||||||
return s
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *Response) Marshal() []byte {
|
func (r *Response) Marshal() []byte {
|
||||||
a := make([]byte, 0, 20)
|
a := make([]byte, 0, 20)
|
||||||
a = append(a, r.header.marshal()...)
|
a = append(a, r.header.marshal()...)
|
||||||
if len(r.operationAttributes) > 0 {
|
if len(r.a.operation) > 0 {
|
||||||
a = append(a, byte(operationAttributes))
|
a = append(a, byte(operationAttributes))
|
||||||
for _, e := range r.operationAttributes {
|
for _, e := range r.a.operation {
|
||||||
a = append(a, e.marshal()...)
|
a = append(a, e.marshal()...)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if len(r.jobAttributes) > 0 {
|
if len(r.a.job) > 0 {
|
||||||
a = append(a, byte(jobAttributes))
|
a = append(a, byte(jobAttributes))
|
||||||
for _, e := range r.jobAttributes {
|
for _, e := range r.a.job {
|
||||||
a = append(a, e.marshal()...)
|
a = append(a, e.marshal()...)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if len(r.printerAttributes) > 0 {
|
if len(r.a.printer) > 0 {
|
||||||
a = append(a, byte(printerAttributes))
|
a = append(a, byte(printerAttributes))
|
||||||
for _, e := range r.printerAttributes {
|
for _, e := range r.a.printer {
|
||||||
a = append(a, e.marshal()...)
|
a = append(a, e.marshal()...)
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
a = append(a, byte(endOfAttributes))
|
a = append(a, byte(endOfAttributes))
|
||||||
return a
|
return a
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (r *Response) UnMarshal(body io.Reader) {
|
||||||
|
r.header.unmarshal(body)
|
||||||
|
//log.Printf("Header %v", r.header)
|
||||||
|
r.a = UnMarshalAttributues(body)
|
||||||
|
}
|
||||||
|
|
||||||
func (r *Response) AddPrinterAttribute(a Attribute) {
|
func (r *Response) AddPrinterAttribute(a Attribute) {
|
||||||
r.printerAttributes = append(r.printerAttributes, a)
|
r.a.addAttribute(printerAttributes, a)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *Response) AddOperatonAttribute(a Attribute) {
|
func (r *Response) AddOperatonAttribute(a Attribute) {
|
||||||
r.operationAttributes = append(r.operationAttributes, a)
|
r.a.addAttribute(operationAttributes, a)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *Response) AddJobAttribute(a Attribute) {
|
func (r *Response) AddJobAttribute(a Attribute) {
|
||||||
r.jobAttributes = append(r.jobAttributes, a)
|
r.a.addAttribute(jobAttributes, a)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -14,9 +14,14 @@ func NewtextWithoutLanguage(name, value string) *textWithoutLanguage {
|
|||||||
return c
|
return c
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (c textWithoutLanguage) Name() string {
|
||||||
|
return c.name
|
||||||
|
}
|
||||||
|
|
||||||
func (c textWithoutLanguage) String() string {
|
func (c textWithoutLanguage) String() string {
|
||||||
return c.name + ":" + c.value
|
return c.name + ":" + c.value
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *textWithoutLanguage) valueTag() tag {
|
func (c *textWithoutLanguage) valueTag() tag {
|
||||||
return textWithoutLanguageValueTag
|
return textWithoutLanguageValueTag
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,6 +16,10 @@ func NewUriValue(name, value string) *uriValue {
|
|||||||
return u
|
return u
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (u uriValue) Name() string {
|
||||||
|
return u.name
|
||||||
|
}
|
||||||
|
|
||||||
func (u uriValue) String() string {
|
func (u uriValue) String() string {
|
||||||
return u.name + ":" + u.value
|
return u.name + ":" + u.value
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user