Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Executor #1016

Merged
merged 82 commits into from
Jan 27, 2020
Merged
Show file tree
Hide file tree
Changes from 27 commits
Commits
Show all changes
82 commits
Select commit Hold shift + click to select a range
11d88f6
executor initial commit
ukclivecox Sep 29, 2019
c5c58d5
initial e2e processing
ukclivecox Sep 29, 2019
f795b1b
Merge branch 'master' into executor
ukclivecox Oct 1, 2019
f24f6ee
Merge branch 'master' into executor
ukclivecox Oct 4, 2019
ac827cb
update to refector and test transform - WIP
ukclivecox Oct 5, 2019
188392a
generalize executor payloads
ukclivecox Oct 7, 2019
598b13f
update executor transform
ukclivecox Oct 8, 2019
7b3445f
Merge branch 'master' into executor
ukclivecox Oct 12, 2019
c61136b
add full predictor process
ukclivecox Oct 12, 2019
2ab8b5b
rest client tests
ukclivecox Oct 13, 2019
b81f5de
correct type annotation for aggregate
ukclivecox Oct 13, 2019
8710ff8
go fmt
ukclivecox Oct 13, 2019
aaaf941
go vet
ukclivecox Oct 13, 2019
59b34b5
incorporate into operator
ukclivecox Oct 14, 2019
88f17c9
client updates
ukclivecox Oct 15, 2019
00e57f2
updated mean classifier
ukclivecox Oct 15, 2019
eb8219b
add proto folder
ukclivecox Oct 17, 2019
61077fb
initial grpc commit
ukclivecox Oct 17, 2019
49a7b69
grpc client initial commit
ukclivecox Oct 22, 2019
4083d9f
finish grpc server
ukclivecox Oct 23, 2019
da9ab75
rebase
ukclivecox Oct 23, 2019
e52cb74
Add rest server tests
ukclivecox Oct 23, 2019
ff04ed7
Add grpc tests
ukclivecox Oct 23, 2019
db3ba06
Add README
ukclivecox Oct 23, 2019
583b54d
rebase
ukclivecox Oct 29, 2019
f83875c
Basic testing for model and abtests
ukclivecox Oct 29, 2019
dc3b5c5
Update test for AB test
ukclivecox Oct 29, 2019
a52af14
Merge branch 'master' into executor
ukclivecox Dec 7, 2019
d61ee53
review updates and content type handling
ukclivecox Dec 7, 2019
2dab328
initial generic processing
ukclivecox Dec 9, 2019
4fc0346
rebase
ukclivecox Dec 20, 2019
6b540d1
lint updates and clean Makefile
ukclivecox Dec 20, 2019
b70ee3e
use operator types and clientset
ukclivecox Dec 20, 2019
cd02dea
add JSON rest client with test
ukclivecox Dec 20, 2019
e724c54
Merge branch 'master' into executor
ukclivecox Dec 23, 2019
1b5a1f2
Add new logger
ukclivecox Dec 24, 2019
14174fe
run linter
ukclivecox Dec 24, 2019
42789d2
Add open tracing to executor
ukclivecox Dec 24, 2019
2a29e75
Add logger sample
ukclivecox Dec 24, 2019
d0001c5
Allow tensorflow protocol for REST
ukclivecox Dec 26, 2019
5d2f03a
package restructure
ukclivecox Dec 26, 2019
e9172ef
add tensorflow grpc
ukclivecox Dec 26, 2019
6c827e0
add tf
ukclivecox Dec 26, 2019
1bcd2d8
add protos
ukclivecox Dec 27, 2019
304df26
Add tfserving example
ukclivecox Dec 27, 2019
6d25b25
add REST metrics
ukclivecox Jan 1, 2020
2eeb443
Add grpc prometheus metrics
ukclivecox Jan 3, 2020
6175b9b
clean up
ukclivecox Jan 4, 2020
e41c9b0
Update README
ukclivecox Jan 4, 2020
fb86cdd
Merge branch 'master' into executor
ukclivecox Jan 4, 2020
90ca514
Update helm charts on testing
ukclivecox Jan 4, 2020
f12cde6
Add executor helm variables
ukclivecox Jan 4, 2020
18c892e
update tests
ukclivecox Jan 5, 2020
7e2b1c7
Add feedback
ukclivecox Jan 6, 2020
4e2a681
Updates from e2e tests
ukclivecox Jan 7, 2020
a3b05b3
Update ingress so seldon and tensorflow work
ukclivecox Jan 8, 2020
6de4651
Add status for REST
ukclivecox Jan 10, 2020
4da41fa
Add tensorflow model status
ukclivecox Jan 10, 2020
0bd64ff
Add metadata endpoints
ukclivecox Jan 11, 2020
96fa7da
python linter
ukclivecox Jan 11, 2020
980ea29
add seldon puid to rest
ukclivecox Jan 11, 2020
1f6d771
lint
ukclivecox Jan 11, 2020
e87b4e3
updates docs and tracing example
ukclivecox Jan 12, 2020
7b45d23
Update seldon id logging and context pass thru
ukclivecox Jan 12, 2020
28f66e4
add metrics examples and docs
ukclivecox Jan 14, 2020
b1630d8
Update tensorflow serving prepacked server creation
ukclivecox Jan 16, 2020
5921b70
Add logging docs and example
ukclivecox Jan 18, 2020
8d5af50
Add header pass thru and more tests
ukclivecox Jan 18, 2020
10f5c33
Docs update
ukclivecox Jan 18, 2020
da09ef3
rebase
ukclivecox Jan 19, 2020
5124471
update tests
ukclivecox Jan 20, 2020
f25753c
add docs for new metadata endpoint
ukclivecox Jan 20, 2020
04dfb56
update from code review
ukclivecox Jan 20, 2020
2fd3ff4
Update from testing example notebooks
ukclivecox Jan 21, 2020
79d94a7
Fix typos from review
ukclivecox Jan 22, 2020
90cde35
Update grpc server receivers
ukclivecox Jan 23, 2020
f66f773
fix typo
ukclivecox Jan 23, 2020
fbc8e94
rebase
ukclivecox Jan 23, 2020
aeca664
remove grpc test due to Ambassador issues
ukclivecox Jan 23, 2020
fbe3405
add 3rd party licenses
ukclivecox Jan 24, 2020
47bae1d
Add license readme
ukclivecox Jan 24, 2020
9935d6e
Use dot imports for tests
ukclivecox Jan 24, 2020
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions examples/models/mean_classifier/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,9 @@ build_grpc:

push_grpc:
docker push ${IMAGE_BASE}_grpc:${VERSION}

run_rest_local:
export PREDICTIVE_UNIT_SERVICE_PORT=9000 && seldon-core-microservice --service-type MODEL MeanClassifier REST

run_grpc_local:
export PREDICTIVE_UNIT_SERVICE_PORT=9000 && seldon-core-microservice --service-type MODEL MeanClassifier GRPC
8 changes: 8 additions & 0 deletions executor/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
./executor
./vendor
./tensorflow
./serving
./bin
./cover.out
./executor.tar

27 changes: 27 additions & 0 deletions executor/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
# Build the manager binary
FROM golang:1.12.5 as builder
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why not 1.13?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I copied an old base. Will update.


WORKDIR /workspace
# Copy the Go Modules manifests
COPY go.mod go.mod
COPY go.sum go.sum
COPY proto/ proto/
# cache deps before building and copying source so that we don't need to re-download as much
# and so that source changes don't invalidate our downloaded layer
RUN go mod download

# Copy the go source
COPY main.go main.go
COPY api/ api/
COPY client/ client/
COPY predictor/ predictor/

# Build
RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 GO111MODULE=on go build -a -o executor main.go

# Use distroless as minimal base image to package the manager binary
# Refer to https://github.com/GoogleContainerTools/distroless for more details
FROM gcr.io/distroless/static:latest
WORKDIR /
COPY --from=builder /workspace/executor .
ENTRYPOINT ["/executor"]
79 changes: 79 additions & 0 deletions executor/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
VERSION := $(shell cat ../version.txt)
# Image URL to use all building/pushing image targets
IMG ?= seldonio/seldon-core-executor:${VERSION}

# Get the currently used golang install path (in GOPATH/bin, unless GOBIN is set)
ifeq (,$(shell go env GOBIN))
GOBIN=$(shell go env GOPATH)/bin
else
GOBIN=$(shell go env GOBIN)
endif

# Run go fmt against code
fmt:
go fmt ./...

# Run go vet against code
vet:
go vet ./...


# Build manager binary
executor: fmt vet
go build -o executor main.go


.PHONY: copy_protos
copy_protos:
cp -r ../proto/tensorflow/tensorflow/** proto/tensorflow


.PHONY: compile_seldon_proto
compile_seldon_proto:
cp ../proto/prediction.proto api/grpc
cd api/grpc && protoc -I. -I${GOPATH}/src/github.com/tensorflow/tensorflow --go_out=paths=source_relative,plugins=grpc:. prediction.proto
rm api/grpc/prediction.proto

# https://github.com/tensorflow/serving/issues/1365#issuecomment-525351995
.PHONY: compile_tensorflow_proto
compile_tensorflow_proto:
git clone -b r1.15 https://github.com/tensorflow/tensorflow.git
git clone -b r1.14 https://github.com/tensorflow/serving.git
go run protoc.go
go mod edit -replace=github.com/tensorflow/tensorflow/tensorflow/go/core=./proto/tensorflow/core
cd proto/tensorflow/core && go mod init github.com/tensorflow/tensorflow/tensorflow/go/core && cd -
go build ./proto/tensorflow/serving

# Run tests
test: fmt vet
go test ./api/... ./predictor/... -coverprofile cover.out

# Build the docker image
docker-build: test
docker build . -t ${IMG}

# Push the docker image
docker-push:
docker push ${IMG}


kind-image-install: docker-build
docker save ${IMG} > executor.tar
kind load image-archive executor.tar --loglevel trace


.PHONY: test_grpc_local
test_grpc_local:
cd proto && grpcurl -plaintext -proto ./prediction.proto 0.0.0.0:8000 seldon.protos.Seldon/Predict

.PHONY: clean
clean:
rm -rf vendor
rm -rf tensorflow
rm -rf serving

start_test_grpc_server:
./executor --sdep seldon-model --namespace default --predictor example --file samples/model_test_grpc.yaml --http_port 8000 -- grpc_port 5000

test_grpc_local:
cd proto && grpcurl -d '{"data":{"ndarray":[[1.0,2.0]]}}' -plaintext -proto ./prediction.proto 0.0.0.0:5000 seldon.protos.Seldon/Predict
65 changes: 65 additions & 0 deletions executor/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
# Seldon Executor

This Go project replaces the Seldon Java Engine. It is presently in development.

** Do not use in production **


## Functionality

The focus is to provide a smaller more efficient graph orchestror. It itends t provide:
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

itends t => intends to (I assume you are using a macbook pro with hectic keyboard.)


* http REST Seldon protocol server for Seldon graphs.
* grpc Seldon protocol server for Seldon graphs.
* Ability to handle other protocols in future, e.g. Tensorflow or NVIDIA TensorRT Server.
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would tracing still be supported by executor?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. I think this should be supported.


The REST and gRPC server are more restricted in that:

* Only 1 is active and it assume your entire graph made up of REST or gRPC components. Mixing is not allowed.

The executor at present will not include functionality presently in the Java engine which will need to be provided elsewhere. Specifically:

* No request logging
* The roadmap will be to use the kfserving InferenceLogger we are proposing in that project and update the Seldon Deployment schema to allow that to be injected as needd.
* No graph metrics
* The roadmap will be to assume each graph component exposes their own Prometheus metrics
* No meta data additions
* It will be assumed this will be done by graph components.

To realise some of the above the Seldon Wrappers will need to be extended.

## Testing

You can choose to use this executor by adding the annotation `seldon.io/executor: "true"`. This annotation will be active until this project progresses from incubating status.

An example is shown below:

```JSON
apiVersion: machinelearning.seldon.io/v1alpha2
kind: SeldonDeployment
metadata:
labels:
app: seldon
name: seldon-model
spec:
annotations:
seldon.io/executor: "true"
name: test-deployment
predictors:
- componentSpecs:
- spec:
containers:
- image: seldonio/mock_classifier_rest:1.3
name: classifier
graph:
children: []
endpoint:
type: REST
name: classifier
type: MODEL
labels:
version: v1
name: example
replicas: 1

```
39 changes: 39 additions & 0 deletions executor/api/client/client.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package client

import (
"fmt"
"github.com/seldonio/seldon-core/executor/api/payload"
"golang.org/x/xerrors"
"io"
)

type SeldonApiClient interface {
Predict(host string, port int32, msg payload.SeldonPayload) (payload.SeldonPayload, error)
TransformInput(host string, port int32, msg payload.SeldonPayload) (payload.SeldonPayload, error)
Route(host string, port int32, msg payload.SeldonPayload) (int, error)
Combine(host string, port int32, msgs []payload.SeldonPayload) (payload.SeldonPayload, error)
TransformOutput(host string, port int32, msg payload.SeldonPayload) (payload.SeldonPayload, error)
Unmarshall(msg []byte) (payload.SeldonPayload, error)
Marshall(out io.Writer, msg payload.SeldonPayload) error
CreateErrorPayload(err error) payload.SeldonPayload
}

type SeldonApiError struct {
Message string
Code int
frame xerrors.Frame
}

func (se SeldonApiError) FormatError(p xerrors.Printer) error {
p.Printf("%d %s", se.Code, se.Message)
se.frame.Format(p)
return nil
}

func (se SeldonApiError) Format(f fmt.State, c rune) {
xerrors.FormatError(se, f, c)
}

func (se SeldonApiError) Error() string {
return fmt.Sprint(se)
}
66 changes: 66 additions & 0 deletions executor/api/client/seldondeployment_client.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
package client

import (
"fmt"
"github.com/go-logr/logr"
"github.com/seldonio/seldon-core/executor/api/machinelearning/v1alpha2"
clientset "github.com/seldonio/seldon-core/executor/client/clientset/versioned/typed/machinelearning/v1alpha2"
v1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/rest"
"k8s.io/client-go/tools/clientcmd"
"k8s.io/client-go/util/homedir"
"path/filepath"
logf "sigs.k8s.io/controller-runtime/pkg/runtime/log"
)

type SeldonDeploymentClient struct {
client *clientset.MachinelearningV1alpha2Client
Log logr.Logger
}

func NewSeldonDeploymentClient(path *string) *SeldonDeploymentClient {

var config *rest.Config
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

var err error
if path != nil && *path != "" {
config, err = clientcmd.BuildConfigFromFlags("", *path)
if err != nil {
panic(err.Error())
}
} else {
config, err = rest.InClusterConfig()
if err != nil {
if home := homedir.HomeDir(); home != "" {
homepath := filepath.Join(home, ".kube", "config")
config, err = clientcmd.BuildConfigFromFlags("", homepath)
if err != nil {
panic(err.Error())
}
}
}
}

kubeClientset, err := clientset.NewForConfig(config)
if err != nil {
panic(err.Error())
}

return &SeldonDeploymentClient{
kubeClientset,
logf.Log.WithName("SeldonRestApi"),
}
}

func (sd *SeldonDeploymentClient) GetPredcitor(sdepName string, namespace string, predictorName string) (*v1alpha2.PredictorSpec, error) {
sdep, err := sd.client.SeldonDeployments(namespace).Get(sdepName, v1.GetOptions{})
if err != nil {
return nil, err
}
for _, predictor := range sdep.Spec.Predictors {
if predictor.Name == predictorName {
return &predictor, nil
}
}

return nil, fmt.Errorf("Failed to find predictor with name %s", predictorName)
}
Loading