diff --git a/core/coreapi/interface/interface.go b/core/coreapi/interface/interface.go index 7809c8b99..3e0e3d460 100644 --- a/core/coreapi/interface/interface.go +++ b/core/coreapi/interface/interface.go @@ -64,6 +64,9 @@ type CoreAPI interface { // Key returns an implementation of Key API. Key() KeyAPI + // ObjectAPI returns an implementation of Object API + Object() ObjectAPI + // ResolvePath resolves the path using Unixfs resolver ResolvePath(context.Context, Path) (Path, error) @@ -205,8 +208,16 @@ type ObjectAPI interface { // * 'unixfs-dir' - Empty UnixFS directory WithType(string) options.ObjectNewOption - // Put imports the node into merkledag - Put(context.Context, Node) (Path, error) + // Put imports the data into merkledag + Put(context.Context, io.Reader, ...options.ObjectPutOption) (Path, error) + + // WithInputEnc is an option for Put which specifies the input encoding of the + // data. Default is "json". + // + // Supported encodings: + // * "protobuf" + // * "json" + WithInputEnc(e string) options.ObjectPutOption // Get returns the node for the path Get(context.Context, Path) (Node, error) diff --git a/core/coreapi/interface/options/object.go b/core/coreapi/interface/options/object.go index 6a144ab2b..fe86a1cde 100644 --- a/core/coreapi/interface/options/object.go +++ b/core/coreapi/interface/options/object.go @@ -4,11 +4,16 @@ type ObjectNewSettings struct { Type string } +type ObjectPutSettings struct { + InputEnc string +} + type ObjectAddLinkSettings struct { Create bool } type ObjectNewOption func(*ObjectNewSettings) error +type ObjectPutOption func(*ObjectPutSettings) error type ObjectAddLinkOption func(*ObjectAddLinkSettings) error func ObjectNewOptions(opts ...ObjectNewOption) (*ObjectNewSettings, error) { @@ -25,6 +30,20 @@ func ObjectNewOptions(opts ...ObjectNewOption) (*ObjectNewSettings, error) { return options, nil } +func ObjectPutOptions(opts ...ObjectPutOption) (*ObjectPutSettings, error) { + options := &ObjectPutSettings{ + InputEnc: "json", + } + + for _, opt := range opts { + err := opt(options) + if err != nil { + return nil, err + } + } + return options, nil +} + func ObjectAddLinkOptions(opts ...ObjectAddLinkOption) (*ObjectAddLinkSettings, error) { options := &ObjectAddLinkSettings{ Create: false, @@ -48,6 +67,13 @@ func (api *ObjectOptions) WithType(t string) ObjectNewOption { } } +func (api *ObjectOptions) WithInputEnc(e string) ObjectPutOption { + return func(settings *ObjectPutSettings) error { + settings.InputEnc = e + return nil + } +} + func (api *ObjectOptions) WithCreate(create bool) ObjectAddLinkOption { return func(settings *ObjectAddLinkSettings) error { settings.Create = create diff --git a/core/coreapi/object.go b/core/coreapi/object.go index 91e6aff65..915c5ed8c 100644 --- a/core/coreapi/object.go +++ b/core/coreapi/object.go @@ -3,7 +3,6 @@ package coreapi import ( "bytes" "context" - "errors" "io" "io/ioutil" @@ -15,6 +14,7 @@ import ( ft "github.com/ipfs/go-ipfs/unixfs" node "gx/ipfs/QmNwUEK7QbwSqyKBu3mMtToo8SUc6wQJ7gdZq4gGGJqfnf/go-ipld-format" + cid "gx/ipfs/QmeSrf6pzut73u6zLQkRFQ3ygt3k6XFT2kjdYP8Tnkwwyg/go-cid" ) type ObjectAPI struct { @@ -43,8 +43,14 @@ func (api *ObjectAPI) New(ctx context.Context, opts ...caopts.ObjectNewOption) ( return n, nil } -func (api *ObjectAPI) Put(context.Context, coreiface.Node) (coreiface.Path, error) { - return nil, errors.New("todo") // TODO: implement using dag api. +func (api *ObjectAPI) Put(ctx context.Context, src io.Reader, opts ...caopts.ObjectPutOption) (coreiface.Path, error) { + options, err := caopts.ObjectPutOptions(opts...) + if err != nil { + return nil, err + } + + dagApi := api.Dag() + return dagApi.Put(ctx, src, dagApi.WithInputEnc(options.InputEnc), dagApi.WithCodec(cid.DagProtobuf)) } func (api *ObjectAPI) Get(ctx context.Context, path coreiface.Path) (coreiface.Node, error) { diff --git a/core/coredag/dagtransl.go b/core/coredag/dagtransl.go index 10a76c052..c17a677a2 100644 --- a/core/coredag/dagtransl.go +++ b/core/coredag/dagtransl.go @@ -18,9 +18,10 @@ type InputEncParsers map[string]FormatParsers // DefaultInputEncParsers is InputEncParser that is used everywhere var DefaultInputEncParsers = InputEncParsers{ - "json": defaultJSONParsers, - "raw": defaultRawParsers, - "cbor": defaultCborParsers, + "json": defaultJSONParsers, + "raw": defaultRawParsers, + "cbor": defaultCborParsers, + "protobuf": defaultProtobufParsers, } var defaultJSONParsers = FormatParsers{ @@ -46,6 +47,11 @@ var defaultCborParsers = FormatParsers{ "dag-cbor": cborRawParser, } +var defaultProtobufParsers = FormatParsers{ + "protobuf": dagpbRawParser, + "dag-pb": dagpbRawParser, +} + // ParseInputs uses DefaultInputEncParsers to parse io.Reader described by // input encoding and format to an instance of ipld Node func ParseInputs(ienc, format string, r io.Reader, mhType uint64, mhLen int) ([]node.Node, error) {