diff --git a/context.go b/context.go index f6ad7b4..69a5db5 100644 --- a/context.go +++ b/context.go @@ -12,7 +12,6 @@ import ( "runtime" "sync" "github.com/google/uuid" - "encoding" badger "github.com/dgraph-io/badger/v3" ) @@ -1223,7 +1222,7 @@ func NewContext(db * badger.DB, log Logger) (*Context, error) { data = nil } else { data = make([]byte, 8) - time_ser, err := value.Interface().(encoding.BinaryMarshaler).MarshalBinary() + time_ser, err := value.Interface().(time.Time).GobEncode() if err != nil { return SerializedValue{}, err } @@ -1249,9 +1248,10 @@ func NewContext(db * badger.DB, log Logger) (*Context, error) { } data := value.Data[0:ser_size] value.Data = value.Data[ser_size:] - time_value := reflect.New(reflect.TypeOf(time.Time{})).Elem() - time_value.Addr().Interface().(encoding.BinaryUnmarshaler).UnmarshalBinary(data) - return time_value.Type(), &time_value, value, nil + time_value := reflect.New(reflect.TypeOf(time.Time{})) + time_value.Interface().(*time.Time).GobDecode(data) + time_nonptr := time_value.Elem() + return time_nonptr.Type(), &time_nonptr, value, nil } }) diff --git a/gql.go b/gql.go index 98d93f9..c443f13 100644 --- a/gql.go +++ b/gql.go @@ -16,6 +16,7 @@ import ( "encoding/json" "fmt" "io" + "os" "net" "net/http" "reflect" @@ -1763,6 +1764,29 @@ func NewGQLExt(ctx *Context, listen string, tls_cert []byte, tls_key []byte) (*G }, nil } +// Returns "${base}/${path}" if it's a file or "${base}/${path}/index.html" if it's a directory +// Returns os.ErrInvalid if "${base}/${path}/index.html" is a directory +func getContentPath(base string, path string) (string, error) { + full_path := fmt.Sprintf("%s%s", base, path) + path_info, err := os.Stat(full_path) + + if err != nil && err != os.ErrNotExist { + return "", err + } else if path_info.IsDir() == true { + index_path := fmt.Sprintf("%s%s/index.html", base, path) + index_info, err := os.Stat(index_path) + if err != nil { + return "", err + } else if index_info.IsDir() == true { + return index_path, os.ErrInvalid + } else { + return index_path, nil + } + } else { + return full_path, nil + } +} + func (ext *GQLExt) StartGQLServer(ctx *Context, node *Node) error { if ext.tcp_listener != nil || ext.http_server != nil { return fmt.Errorf("listener or server is still running, stop them first") @@ -1774,8 +1798,27 @@ func (ext *GQLExt) StartGQLServer(ctx *Context, node *Node) error { mux.HandleFunc("/graphiql", GraphiQLHandler()) // Server the ./site directory to /site (TODO make configurable with better defaults) - fs := http.FileServer(http.Dir("./site")) - mux.Handle("/site/", http.StripPrefix("/site", fs)) + + mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request){ + custom_path, err_1 := getContentPath("./custom", r.URL.Path) + if err_1 != nil { + static_path, err_2 := getContentPath("./site", r.URL.Path) + if err_2 != nil { + ctx.Log.Logf("gql", "File Resolve errors: %s - %s", err_1, err_2) + w.Header().Add("Content-Type", "application/json") + w.WriteHeader(501) + w.Write([]byte("{\"error\": \"server_error\"}")) + } else { + ctx.Log.Logf("gql", "STATIC_FILE: %s", static_path) + w.WriteHeader(200) + http.ServeFile(w, r, static_path) + } + } else { + ctx.Log.Logf("gql", "CUSTOM_FILE: %s", custom_path) + w.WriteHeader(200) + http.ServeFile(w, r, custom_path) + } + }) http_server := &http.Server{ Addr: ext.Listen, diff --git a/serialize_test.go b/serialize_test.go index dfa11ef..4cd3e30 100644 --- a/serialize_test.go +++ b/serialize_test.go @@ -29,7 +29,7 @@ func TestSerializeBasic(t *testing.T) { testSerializeComparable[int32](t, ctx, int32(-12345)) testSerializeComparable[int64](t, ctx, int64(-123456)) testSerializeComparable[time.Duration](t, ctx, time.Duration(100)) - testSerializeComparable[time.Time](t, ctx, time.Now()) + testSerializeComparable[time.Time](t, ctx, time.Now().Truncate(0)) testSerializeSlice[[]int](t, ctx, []int{123, 456, 789, 101112}) testSerializeSlice[[]int](t, ctx, ([]int)(nil)) testSerializeSliceSlice[[][]int](t, ctx, [][]int{{123, 456, 789, 101112}, {3253, 2341, 735, 212}, {123, 51}, nil})