package xgb

import (
	"errors"
)

// Cookie is the internal representation of a cookie, where one is generated
// for *every* request sent by XGB.
// 'cookie' is most frequently used by embedding it into a more specific
// kind of cookie, i.e., 'GetInputFocusCookie'.
type Cookie struct {
	conn      *Conn
	Sequence  uint16
	replyChan chan []byte
	errorChan chan error
	pingChan  chan bool
}

// NewCookie creates a new cookie with the correct channels initialized
// depending upon the values of 'checked' and 'reply'. Together, there are
// four different kinds of cookies. (See more detailed comments in the
// function for more info on those.)
// Note that a sequence number is not set until just before the request
// corresponding to this cookie is sent over the wire.
//
// Unless you're building requests from bytes by hand, this method should
// not be used.
func (c *Conn) NewCookie(checked, reply bool) *Cookie {
	cookie := &Cookie{
		conn:      c,
		Sequence:  0, // we add the sequence id just before sending a request
		replyChan: nil,
		errorChan: nil,
		pingChan:  nil,
	}

	// There are four different kinds of cookies:
	// Checked requests with replies get a reply channel and an error channel.
	// Unchecked requests with replies get a reply channel and a ping channel.
	// Checked requests w/o replies get a ping channel and an error channel.
	// Unchecked requests w/o replies get no channels.
	// The reply channel is used to send reply data.
	// The error channel is used to send error data.
	// The ping channel is used when one of the 'reply' or 'error' channels
	// is missing but the other is present. The ping channel is way to force
	// the blocking to stop and basically say "the error has been received
	// in the main event loop" (when the ping channel is coupled with a reply
	// channel) or "the request you made that has no reply was successful"
	// (when the ping channel is coupled with an error channel).
	if checked {
		cookie.errorChan = make(chan error, 1)
		if !reply {
			cookie.pingChan = make(chan bool, 1)
		}
	}
	if reply {
		cookie.replyChan = make(chan []byte, 1)
		if !checked {
			cookie.pingChan = make(chan bool, 1)
		}
	}

	return cookie
}

// Reply detects whether this is a checked or unchecked cookie, and calls
// 'replyChecked' or 'replyUnchecked' appropriately.
//
// Unless you're building requests from bytes by hand, this method should
// not be used.
func (c Cookie) Reply() ([]byte, error) {
	// checked
	if c.errorChan != nil {
		return c.replyChecked()
	}
	return c.replyUnchecked()
}

// replyChecked waits for a response on either the replyChan or errorChan
// channels. If the former arrives, the bytes are returned with a nil error.
// If the latter arrives, no bytes are returned (nil) and the error received
// is returned.
//
// Unless you're building requests from bytes by hand, this method should
// not be used.
func (c Cookie) replyChecked() ([]byte, error) {
	if c.replyChan == nil {
		return nil, errors.New("Cannot call 'replyChecked' on a cookie that " +
			"is not expecting a *reply* or an error.")
	}
	if c.errorChan == nil {
		return nil, errors.New("Cannot call 'replyChecked' on a cookie that " +
			"is not expecting a reply or an *error*.")
	}

	select {
	case reply := <-c.replyChan:
		return reply, nil
	case err := <-c.errorChan:
		return nil, err
	}
}

// replyUnchecked waits for a response on either the replyChan or pingChan
// channels. If the former arrives, the bytes are returned with a nil error.
// If the latter arrives, no bytes are returned (nil) and a nil error
// is returned. (In the latter case, the corresponding error can be retrieved
// from (Wait|Poll)ForEvent asynchronously.)
// In all honesty, you *probably* don't want to use this method.
//
// Unless you're building requests from bytes by hand, this method should
// not be used.
func (c Cookie) replyUnchecked() ([]byte, error) {
	if c.replyChan == nil {
		return nil, errors.New("Cannot call 'replyUnchecked' on a cookie " +
			"that is not expecting a *reply*.")
	}

	select {
	case reply := <-c.replyChan:
		return reply, nil
	case <-c.pingChan:
		return nil, nil
	}
}

// Check is used for checked requests that have no replies. It is a mechanism
// by which to report "success" or "error" in a synchronous fashion. (Therefore,
// unchecked requests without replies cannot use this method.)
// If the request causes an error, it is sent to this cookie's errorChan.
// If the request was successful, there is no response from the server.
// Thus, pingChan is sent a value when the *next* reply is read.
// If no more replies are being processed, we force a round trip request with
// GetInputFocus.
//
// Unless you're building requests from bytes by hand, this method should
// not be used.
func (c Cookie) Check() error {
	if c.replyChan != nil {
		return errors.New("Cannot call 'Check' on a cookie that is " +
			"expecting a *reply*. Use 'Reply' instead.")
	}
	if c.errorChan == nil {
		return errors.New("Cannot call 'Check' on a cookie that is " +
			"not expecting a possible *error*.")
	}

	// First do a quick non-blocking check to see if we've been pinged.
	select {
	case err := <-c.errorChan:
		return err
	case <-c.pingChan:
		return nil
	default:
	}

	// Now force a round trip and try again, but block this time.
	c.conn.Sync()
	select {
	case err := <-c.errorChan:
		return err
	case <-c.pingChan:
		return nil
	}
}
