semrush / zenrpc Goto Github PK
View Code? Open in Web Editor NEWJSON-RPC 2.0 Server Implementation with SMD support written in Go (go generate)
License: MIT License
JSON-RPC 2.0 Server Implementation with SMD support written in Go (go generate)
License: MIT License
How can I server for example this code below:
jrpc.Register("jrpc", JRPCService{})
jrpc.Register("", JRPCService{}) // public
http.HandleFunc("/hello", func(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Welcome to my website!")
})
currently if I try to open /hello i receive 415 response :(
If I declare the type base on string to use as enum type. Generator will identify its as Object, but its incorrect and would cursed Json Unmarshal failed during processing request. It should be smd.String
.
type Category string
const (
CategoryLatest Category = "latest"
CategoryNews = "news"
)
func (s DataService) GetRecommendStreams(category Category) ([]string, error) {
}
...
GetRecommendStreams": {
Description: `TODO: deal with type problem,to made zenrpc support string enum or similar problem`,
Parameters: []smd.JSONSchema{
{
Name: "category",
Optional: false,
Description: ``,
Type: smd.Object, //<--- Problem here
Properties: map[string]smd.Property{},
},
},
Returns: smd.JSONSchema{
Description: ``,
Optional: false,
Type: smd.Array,
Items: map[string]string{
"type": smd.String,
},
},
},
...
request ID needs to be present in middleware logger string
probably related to #13
Setting default value for string parameters with space(s) causes generator error.
Example code:
// Echo returns input string.
//zenrpc:to="John Doe" name goes here
func (s *Say) Hello(to string) string {
return fmt.Sprintf("Hey, %v!", to)
}
What I got:
> go generate src/rpc/rpc.go
Generator version: 1.0.1
Entrypoint: rpc.go
Error: 85:23: string literal not terminated
Currently we have following signature:
//zenrpc:<method parameter>[:<default value>][whitespaces<description>]
Let's change [:<default value>]
to [=<default value>]
for readability.
Setting a default value through magic comments, e.g.:
//zenrpc:bar="bar" Foobar
func (srv Service) Foo(ctx contect.Context, foo string) (*Result, *zenrpc.Error) {
// ...
}
Appear not too generate a Default value in the SMD:
{
Name: "foo",
Optional: true,
Description: `Foobar`,
Type: smd.String,
},
Expect something ala:
_MfooAbar_defaultJSON, _ := json.Marshal("bar")
// ...
{
Name: "foo",
Optional: true,
Description: `Foobar`,
Type: smd.String,
Default: json.RawMessage(_MfooAbar_defaultJSON),
},
zenrpc version v1.0.1
Sometimes it matters which word convention do you use.
For example, in some projects it is a rule to use only snake_case in json properties.
Now we do not have any options for the problem. I suggest to add some flag for word convention.
Hi
We love zenrpc.
We just experienced the zenrpc code generator being very slow. We have a small project which about 10 methods in 2 files, which takes zenrpc more than 1 minutes to generate. And the CPU usage are very high during the generating process.
Currently time.Time
parameter in service method produces object
type in SMD schema. But it should be a string
.
You can find the fix here devimteam@1f71750
Please provide example Middileware func that runs before request is precessed but after rpc acquires method and params for request.
Needed for uuid generation for specific request.
Hi. I have a similar problem with the link, but the solution did not help me.
error : "running "zenrpc": exec: "zenrpc": executable file not found in %PATH%"
Hi, this fix #26 didn't work with another type of recursive structs
Code
package main
import (
"context"
"flag"
"log"
"net/http"
"os"
"github.com/semrush/zenrpc"
)
type MyModelWithRef struct {
Model *MyModel
}
type MyModel struct {
List []*MyModelWithRef
}
type MyService struct{ zenrpc.Service }
func (s MyService) SomeMethod(ctx context.Context, model MyModel) error {
return nil
}
//go:generate zenrpc
func main() {
addr := flag.String("addr", "localhost:9999", "listen address")
flag.Parse()
rpc := zenrpc.NewServer(zenrpc.Options{ExposeSMD: true})
rpc.Register("service", MyService{})
rpc.Use(zenrpc.Logger(log.New(os.Stderr, "", log.LstdFlags)))
http.Handle("/", rpc)
log.Printf("starting on %s", *addr)
log.Fatal(http.ListenAndServe(*addr, nil))
}
Error
Generator version: 1.0.1
Entrypoint: ./
runtime: goroutine stack exceeds 1000000000-byte limit
fatal error: stack overflow
package example
import "pkg/bar"
//go:generate zenrpc
type Service struct {
zenrpc.Service
}
func (s Service) Func1(ctx context.Context, a string, b int64) error {
return errors.New("not implemented")
}
func (s Service) Func2(ctx context.Context, dat *bar.SomeStruct) error {
return errors.New("not implemented")
}
Если функцию Func2 закоментировать и прогнать go generate то нет зацикливания
When running zenrpc in a package that both defines and imports a zenrpc.Service
type, then it will generate (incorrect) code for the imported services.
I.e. if having:
cmd/mycmd
main_zenrpc.go -- generated
service.go -- defines FooService
server.go -- register FooService and pkg/bar.Service
pkg/bar
bar_zenrpc.go -- generated
service.go -- defines Service
When generating the code in cmd/mycmd
then it will generate code for Service
(which does not exist in the package) as well as FooService, which does exist. It will also, for some reason, import encoding/json
twise. Either way, the result is invalid code.
Maybe related with #35?
When either using named arguments, or when passing arguments into struct parameters, it would be good for the generated zenrpc API to return an error on unkown fields.
This is detectable today in the standard library by initializing a json.Decoder
and calling DisallowUnknownFields
on it.
https://golang.org/pkg/encoding/json/#Decoder.DisallowUnknownFields
The problem with just using json.Unmarshal
as the generated code does today, is that user of the API won't easily discover when they have named parameters wrongly, as there are no clear error messages.
Was wondering if there is currently any way to map parameter names to different names in RPC calls. i.e., having
{
"jsonrpc": "2.0",
"id": 123,
"method": "my.pets",
"params": {
"type": "cats"
}
}
map to
func (MyService) Pets(ctx context.Context, typ string)
project path//zenrpc*": file does not exist,what should i do
Line 85 in 10f2c48
The Definition
type does not allow supplying Items
. This means that even with a custom SMD()
override method, it's not possible to correctly document arrays of arrays where the inner item type is explained.
It seams reasonable to me to just drop the smd.Definition
type and use smd.Property
, or perhaps drop that as well and go for just having the smd.JSONSchema
type.
In addition, the Items
type (map[string]string)
appears odd; the only valid value wold be to supply a key "$ref"
and a value pointing to a Definition, so it would make more sense to let it be of type struct {Ref string `json:"$ref"`}
, or indeed JSONSchema
that already has a Ref
field defined. The latter would also allow for inline schemas.
hello. i use serveWS method and i have case when i need send json-rpc notification while processing request to another clients. for that i need access to websocket connections. what is the best way to implement this with zenrpc?
Take the following example:
type MyService struct {} //zenrpc
type MyArg struct{
A `json:"a"`
B `json:"b"`
}
// DoSomething does something.
//zenrpc:arg specify a and b
func (MyService) DoSomehting(arg MyArg)
I don't see a documented way for providing documentaiton and/or defaults for argument MyArg.A
and MyArg.B
in the struct through magic comments or struct tags/comments.
It would be nice if it was somehow possible. Perhaps as method tags?
//zenrpc:arg.a="default" Let's you document a.
It is a bit inconvenient to expose SMD schema only as an http endpoint.
For example, you might have other tools that work with SMD schema and you could not use them automatically with zenrpc without SMD schema in a file.
Recursive structs causes generator error, even if field marked as ignored
Example code:
type RecursiveJson struct {
Id int `json:"id"`
Parent *RecursiveJson `json:"-"`
}
func (s *Public) Recursive() RecursiveJson {
parent := RecursiveJson{Id: 1}
child := RecursiveJson{Id: 2, Parent: &parent}
return child
}
And I got this, with following call stack
go generate src/rpc/rpc.go
Generator version: 1.0.1
Entrypoint: rpc.go
runtime: goroutine stack exceeds 1000000000-byte limit
fatal error: stack overflow
I didn't check it but I think any ignored fields appears in generated smd
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.