예제 #1
0
파일: input.go 프로젝트: postfix/fwk
func (input *InputStreamer) Connect(ports []fwk.Port) error {
	var err error

	input.ports = make(map[string]fwk.Port, len(ports))

	// FIXME(sbinet): handle multi-reader
	// FIXME(sbinet): handle local/remote files, protocols
	input.r, err = os.Open(input.Names[0])
	if err != nil {
		return err
	}

	input.rio, err = rio.NewReader(input.r)
	if err != nil {
		return err
	}

	recnames := make([]rio.Selector, 0, len(input.ports))
	for _, port := range ports {
		input.ports[port.Name] = port
		rec := input.rio.Record(port.Name)
		err = rec.Connect(port.Name, reflect.New(port.Type))
		if err != nil {
			return err
		}
		recnames = append(recnames, rio.Selector{Name: port.Name, Unpack: true})
	}

	input.scan = rio.NewScanner(input.rio)
	input.scan.Select(recnames)
	return err
}
예제 #2
0
파일: hsvc.go 프로젝트: postfix/fwk
func (svc *hsvc) StartSvc(ctx fwk.Context) error {
	var err error

	for name, stream := range svc.streams {
		switch stream.Mode {
		case Read:
			_, dup := svc.r[name]
			if dup {
				return fwk.Errorf("%s: duplicate read-stream %q", svc.Name(), name)
			}
			// FIXME(sbinet): handle remote/local files + protocols
			f, err := os.Open(stream.Name)
			if err != nil {
				return fwk.Errorf("error opening file [%s]: %v", stream.Name, err)
			}
			r, err := rio.NewReader(f)
			if err != nil {
				return fwk.Errorf("error opening rio-stream [%s]: %v", stream.Name, err)
			}

			svc.r[name] = istream{
				name:  name,
				fname: stream.Name,
				f:     f,
				r:     r,
			}

		case Write:
			_, dup := svc.w[name]
			if dup {
				return fwk.Errorf("%s: duplicate write-stream %q", svc.Name(), name)
			}
			// FIXME(sbinet): handle remote/local files + protocols
			f, err := os.Create(stream.Name)
			if err != nil {
				return fwk.Errorf("error creating file [%s]: %v", stream.Name, err)
			}
			w, err := rio.NewWriter(f)
			if err != nil {
				return fwk.Errorf("error creating rio-stream [%s]: %v", stream.Name, err)
			}

			svc.w[name] = ostream{
				name:  name,
				fname: stream.Name,
				f:     f,
				w:     w,
			}

		default:
			return fwk.Errorf("%s: invalid stream mode (%d)", svc.Name(), stream.Mode)
		}
	}
	return err
}
예제 #3
0
파일: stream.go 프로젝트: postfix/fwk
func (stream *istream) read(name string, ptr interface{}) error {
	var err error

	seekr, ok := stream.f.(io.Seeker)
	if !ok {
		return fwk.Errorf("hbooksvc: input stream [%s] is not seek-able", stream.name)
	}

	pos, err := seekr.Seek(0, 1)
	if err != nil {
		return err
	}
	defer seekr.Seek(pos, 0)

	_, err = seekr.Seek(0, 0)
	if err != nil {
		return err
	}

	r := seekr.(io.Reader)
	rr, err := rio.NewReader(r)
	if err != nil {
		return err
	}
	defer rr.Close()

	scan := rio.NewScanner(rr)
	scan.Select([]rio.Selector{{Name: name, Unpack: true}})
	if !scan.Scan() {
		return scan.Err()
	}
	rec := scan.Record()
	if rec == nil {
		return fwk.Errorf("hbooksvc: could not find record [%s] in stream [%s]", name, stream.name)
	}
	blk := rec.Block(name)
	if blk == nil {
		return fwk.Errorf(
			"hbooksvc: could not get block [%s] from record [%s] in stream [%s]",
			name, name, stream.name,
		)
	}
	err = blk.Read(ptr)
	if err != nil {
		return fwk.Errorf(
			"hbooksvc: could not read data from block [%s] from record [%s] in stream [%s]: %v",
			name, name, stream.name, err,
		)
	}
	return err
}