mirror of
https://github.com/kataras/iris.git
synced 2025-01-23 10:41:03 +01:00
update the nantive-messages(only) example to the latest websocket (minimum changes, the idea is the same) and misc
Former-commit-id: 9598319bc13e8a383114c37f4da84f337ab47b22
This commit is contained in:
parent
8ad4c061d1
commit
33028f900d
|
@ -40,6 +40,15 @@ var bundles = []bundle{
|
||||||
installDir: "./platforms/git",
|
installDir: "./platforms/git",
|
||||||
installArguments: []string{"-InstallDir", "$installDir"},
|
installArguments: []string{"-InstallDir", "$installDir"},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
names: []string{"go"}, // get-only, at least for now.
|
||||||
|
installDir: "./platforms/go",
|
||||||
|
installArguments: []string{"-InstallDir", "$installDir"},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
names: []string{"bombardier"},
|
||||||
|
installDir: "./platforms/bombardier",
|
||||||
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
func install(b bundle) error {
|
func install(b bundle) error {
|
||||||
|
@ -51,6 +60,8 @@ func install(b bundle) error {
|
||||||
return installNode(b)
|
return installNode(b)
|
||||||
case "git":
|
case "git":
|
||||||
return installGit(b)
|
return installGit(b)
|
||||||
|
case "bombardier":
|
||||||
|
return installBombardier(b)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -91,7 +102,7 @@ type platform struct {
|
||||||
|
|
||||||
func (p *platform) text(args ...string) string {
|
func (p *platform) text(args ...string) string {
|
||||||
cmd := exec.Command(p.executable, args...)
|
cmd := exec.Command(p.executable, args...)
|
||||||
b, err := cmd.Output()
|
b, err := cmd.CombinedOutput()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logger.Error(err)
|
logger.Error(err)
|
||||||
return ""
|
return ""
|
||||||
|
@ -111,7 +122,7 @@ func (p *platform) attach(logLevel string, args ...string) error {
|
||||||
return cmd.Run()
|
return cmd.Run()
|
||||||
}
|
}
|
||||||
|
|
||||||
func attachCmd(logLevel string, cmd *exec.Cmd) {
|
func attachCmd(logLevel string, cmd *exec.Cmd) *exec.Cmd {
|
||||||
level := golog.ParseLevel(logLevel)
|
level := golog.ParseLevel(logLevel)
|
||||||
outputReader, err := cmd.StdoutPipe()
|
outputReader, err := cmd.StdoutPipe()
|
||||||
if err == nil {
|
if err == nil {
|
||||||
|
@ -130,11 +141,21 @@ func attachCmd(logLevel string, cmd *exec.Cmd) {
|
||||||
go func() {
|
go func() {
|
||||||
defer errReader.Close()
|
defer errReader.Close()
|
||||||
for errScanner.Scan() {
|
for errScanner.Scan() {
|
||||||
logger.Log(level, errScanner.Text())
|
logger.Log(level, errScanner.Text()) // don't print at error.
|
||||||
}
|
}
|
||||||
}()
|
}()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return cmd
|
||||||
|
}
|
||||||
|
|
||||||
|
func resolveFilename(name string) string {
|
||||||
|
if runtime.GOOS == "windows" {
|
||||||
|
name += ".exe"
|
||||||
|
}
|
||||||
|
|
||||||
|
return name
|
||||||
}
|
}
|
||||||
|
|
||||||
func getPlatform(name string) (p *platform) {
|
func getPlatform(name string) (p *platform) {
|
||||||
|
@ -164,10 +185,7 @@ func getPlatform(name string) (p *platform) {
|
||||||
logger.Fatalf("unable to auto-install %s, please do it yourself: %v", name, err)
|
logger.Fatalf("unable to auto-install %s, please do it yourself: %v", name, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
if runtime.GOOS == "windows" {
|
name = resolveFilename(name)
|
||||||
name += ".exe"
|
|
||||||
}
|
|
||||||
|
|
||||||
// first check for installDir/bin/+name before the installDir/+name to
|
// first check for installDir/bin/+name before the installDir/+name to
|
||||||
// find the installed executable (we could return it from our scripts but we don't).
|
// find the installed executable (we could return it from our scripts but we don't).
|
||||||
binExecutable := b.installDir + "/bin/" + name
|
binExecutable := b.installDir + "/bin/" + name
|
||||||
|
@ -206,5 +224,30 @@ func main() {
|
||||||
gitVersion := git.text("--version")
|
gitVersion := git.text("--version")
|
||||||
logger.Info("Git version: ", gitVersion)
|
logger.Info("Git version: ", gitVersion)
|
||||||
|
|
||||||
os.Stdin.Read(make([]byte, 0))
|
golang := getPlatform("go")
|
||||||
|
goVersion := golang.text("version")
|
||||||
|
logger.Info("Go version: ", goVersion)
|
||||||
|
|
||||||
|
bombardier := getPlatform("bombardier")
|
||||||
|
bombardierVersion := bombardier.text("--version")
|
||||||
|
logger.Info("Bombardier version: ", bombardierVersion)
|
||||||
|
}
|
||||||
|
|
||||||
|
func installBombardier(b bundle) error {
|
||||||
|
const (
|
||||||
|
repo = "github.com/codesenberg/bombardier"
|
||||||
|
latestVersion = "1.2.4"
|
||||||
|
)
|
||||||
|
|
||||||
|
dst := filepath.Join(os.Getenv("GOPATH"), "/src", repo)
|
||||||
|
os.RemoveAll(dst) // remove any copy that $GOPATH may have.
|
||||||
|
|
||||||
|
if err := getPlatform("git").exec("clone", "https://"+repo, dst); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
executable := resolveFilename(b.names[0])
|
||||||
|
executableOutput := filepath.Join(b.installDir, executable)
|
||||||
|
|
||||||
|
return getPlatform("go").attach("info", "build", "-ldflags", "-X main.version="+latestVersion, "-o", executableOutput, dst)
|
||||||
}
|
}
|
||||||
|
|
|
@ -685,6 +685,25 @@ The `iris.Context` source code can be found [here](https://github.com/kataras/ir
|
||||||
// context.Context is very extensible and developers can override
|
// context.Context is very extensible and developers can override
|
||||||
// its methods if that is actually needed.
|
// its methods if that is actually needed.
|
||||||
type Context interface {
|
type Context interface {
|
||||||
|
// BeginRequest is executing once for each request
|
||||||
|
// it should prepare the (new or acquired from pool) context's fields for the new request.
|
||||||
|
//
|
||||||
|
// To follow the iris' flow, developer should:
|
||||||
|
// 1. reset handlers to nil
|
||||||
|
// 2. reset values to empty
|
||||||
|
// 3. reset sessions to nil
|
||||||
|
// 4. reset response writer to the http.ResponseWriter
|
||||||
|
// 5. reset request to the *http.Request
|
||||||
|
// and any other optional steps, depends on dev's application type.
|
||||||
|
BeginRequest(http.ResponseWriter, *http.Request)
|
||||||
|
// EndRequest is executing once after a response to the request was sent and this context is useless or released.
|
||||||
|
//
|
||||||
|
// To follow the iris' flow, developer should:
|
||||||
|
// 1. flush the response writer's result
|
||||||
|
// 2. release the response writer
|
||||||
|
// and any other optional steps, depends on dev's application type.
|
||||||
|
EndRequest()
|
||||||
|
|
||||||
// ResponseWriter returns an http.ResponseWriter compatible response writer, as expected.
|
// ResponseWriter returns an http.ResponseWriter compatible response writer, as expected.
|
||||||
ResponseWriter() ResponseWriter
|
ResponseWriter() ResponseWriter
|
||||||
// ResetResponseWriter should change or upgrade the Context's ResponseWriter.
|
// ResetResponseWriter should change or upgrade the Context's ResponseWriter.
|
||||||
|
@ -692,6 +711,18 @@ type Context interface {
|
||||||
|
|
||||||
// Request returns the original *http.Request, as expected.
|
// Request returns the original *http.Request, as expected.
|
||||||
Request() *http.Request
|
Request() *http.Request
|
||||||
|
// ResetRequest sets the Context's Request,
|
||||||
|
// It is useful to store the new request created by a std *http.Request#WithContext() into Iris' Context.
|
||||||
|
// Use `ResetRequest` when for some reason you want to make a full
|
||||||
|
// override of the *http.Request.
|
||||||
|
// Note that: when you just want to change one of each fields you can use the Request() which returns a pointer to Request,
|
||||||
|
// so the changes will have affect without a full override.
|
||||||
|
// Usage: you use a native http handler which uses the standard "context" package
|
||||||
|
// to get values instead of the Iris' Context#Values():
|
||||||
|
// r := ctx.Request()
|
||||||
|
// stdCtx := context.WithValue(r.Context(), key, val)
|
||||||
|
// ctx.ResetRequest(r.WithContext(stdCtx)).
|
||||||
|
ResetRequest(r *http.Request)
|
||||||
|
|
||||||
// SetCurrentRouteName sets the route's name internally,
|
// SetCurrentRouteName sets the route's name internally,
|
||||||
// in order to be able to find the correct current "read-only" Route when
|
// in order to be able to find the correct current "read-only" Route when
|
||||||
|
@ -732,7 +763,7 @@ type Context interface {
|
||||||
// HandlerIndex sets the current index of the
|
// HandlerIndex sets the current index of the
|
||||||
// current context's handlers chain.
|
// current context's handlers chain.
|
||||||
// If -1 passed then it just returns the
|
// If -1 passed then it just returns the
|
||||||
// current handler index without change the current index.rns that index, useless return value.
|
// current handler index without change the current index.
|
||||||
//
|
//
|
||||||
// Look Handlers(), Next() and StopExecution() too.
|
// Look Handlers(), Next() and StopExecution() too.
|
||||||
HandlerIndex(n int) (currentIndex int)
|
HandlerIndex(n int) (currentIndex int)
|
||||||
|
@ -775,6 +806,12 @@ type Context interface {
|
||||||
Proceed(Handler) bool
|
Proceed(Handler) bool
|
||||||
// HandlerName returns the current handler's name, helpful for debugging.
|
// HandlerName returns the current handler's name, helpful for debugging.
|
||||||
HandlerName() string
|
HandlerName() string
|
||||||
|
// HandlerFileLine returns the current running handler's function source file and line information.
|
||||||
|
// Useful mostly when debugging.
|
||||||
|
HandlerFileLine() (file string, line int)
|
||||||
|
// RouteName returns the route name that this handler is running on.
|
||||||
|
// Note that it will return empty on not found handlers.
|
||||||
|
RouteName() string
|
||||||
// Next calls all the next handler from the handlers chain,
|
// Next calls all the next handler from the handlers chain,
|
||||||
// it should be used inside a middleware.
|
// it should be used inside a middleware.
|
||||||
//
|
//
|
||||||
|
@ -853,7 +890,8 @@ type Context interface {
|
||||||
// that can be used to share information between handlers and middleware.
|
// that can be used to share information between handlers and middleware.
|
||||||
Values() *memstore.Store
|
Values() *memstore.Store
|
||||||
// Translate is the i18n (localization) middleware's function,
|
// Translate is the i18n (localization) middleware's function,
|
||||||
// it calls the Get("translate") to return the translated value.
|
// it calls the Values().Get(ctx.Application().ConfigurationReadOnly().GetTranslateFunctionContextKey())
|
||||||
|
// to execute the translate function and return the localized text value.
|
||||||
//
|
//
|
||||||
// Example: https://github.com/kataras/iris/tree/master/_examples/miscellaneous/i18n
|
// Example: https://github.com/kataras/iris/tree/master/_examples/miscellaneous/i18n
|
||||||
Translate(format string, args ...interface{}) string
|
Translate(format string, args ...interface{}) string
|
||||||
|
@ -870,7 +908,6 @@ type Context interface {
|
||||||
// RequestPath returns the full request path,
|
// RequestPath returns the full request path,
|
||||||
// based on the 'escape'.
|
// based on the 'escape'.
|
||||||
RequestPath(escape bool) string
|
RequestPath(escape bool) string
|
||||||
|
|
||||||
// Host returns the host part of the current url.
|
// Host returns the host part of the current url.
|
||||||
Host() string
|
Host() string
|
||||||
// Subdomain returns the subdomain of this request, if any.
|
// Subdomain returns the subdomain of this request, if any.
|
||||||
|
@ -878,6 +915,9 @@ type Context interface {
|
||||||
Subdomain() (subdomain string)
|
Subdomain() (subdomain string)
|
||||||
// IsWWW returns true if the current subdomain (if any) is www.
|
// IsWWW returns true if the current subdomain (if any) is www.
|
||||||
IsWWW() bool
|
IsWWW() bool
|
||||||
|
// FullRqeuestURI returns the full URI,
|
||||||
|
// including the scheme, the host and the relative requested path/resource.
|
||||||
|
FullRequestURI() string
|
||||||
// RemoteAddr tries to parse and return the real client's request IP.
|
// RemoteAddr tries to parse and return the real client's request IP.
|
||||||
//
|
//
|
||||||
// Based on allowed headers names that can be modified from Configuration.RemoteAddrHeaders.
|
// Based on allowed headers names that can be modified from Configuration.RemoteAddrHeaders.
|
||||||
|
@ -1189,7 +1229,7 @@ type Context interface {
|
||||||
// Note that it has nothing to do with server-side caching.
|
// Note that it has nothing to do with server-side caching.
|
||||||
// It does those checks by checking if the "If-Modified-Since" request header
|
// It does those checks by checking if the "If-Modified-Since" request header
|
||||||
// sent by client or a previous server response header
|
// sent by client or a previous server response header
|
||||||
// (e.g with WriteWithExpiration or StaticEmbedded or Favicon etc.)
|
// (e.g with WriteWithExpiration or HandleDir or Favicon etc.)
|
||||||
// is a valid one and it's before the "modtime".
|
// is a valid one and it's before the "modtime".
|
||||||
//
|
//
|
||||||
// A check for !modtime && err == nil is necessary to make sure that
|
// A check for !modtime && err == nil is necessary to make sure that
|
||||||
|
|
|
@ -10,7 +10,7 @@
|
||||||
However, `neffos.(min.)js` is a NPM package too so alternatively,
|
However, `neffos.(min.)js` is a NPM package too so alternatively,
|
||||||
you can use it as dependency on your package.json and all nodejs-npm tooling become available:
|
you can use it as dependency on your package.json and all nodejs-npm tooling become available:
|
||||||
see the "browserify" example for more-->
|
see the "browserify" example for more-->
|
||||||
<script src="https://cdn.jsdelivr.net/npm/neffos.js@0.1.12/dist/neffos.min.js"></script>
|
<script src="https://cdn.jsdelivr.net/npm/neffos.js@latest/dist/neffos.min.js"></script>
|
||||||
<script>
|
<script>
|
||||||
// `neffos` global variable is available now.
|
// `neffos` global variable is available now.
|
||||||
var scheme = document.location.protocol == "https:" ? "wss" : "ws";
|
var scheme = document.location.protocol == "https:" ? "wss" : "ws";
|
||||||
|
|
|
@ -1,21 +1,13 @@
|
||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"log"
|
||||||
|
|
||||||
"github.com/kataras/iris"
|
"github.com/kataras/iris"
|
||||||
|
|
||||||
"github.com/kataras/iris/websocket"
|
"github.com/kataras/iris/websocket"
|
||||||
)
|
)
|
||||||
|
|
||||||
/* Native messages no need to import the iris-ws.js to the ./templates.client.html
|
|
||||||
Use of: OnMessage and EmitMessage.
|
|
||||||
|
|
||||||
|
|
||||||
NOTICE: IF YOU HAVE RAN THE PREVIOUS EXAMPLES YOU HAVE TO CLEAR YOUR BROWSER's CACHE
|
|
||||||
BECAUSE chat.js is different than the CACHED. OTHERWISE YOU WILL GET Ws is undefined from the browser's console, because it will use the cached.
|
|
||||||
*/
|
|
||||||
|
|
||||||
type clientPage struct {
|
type clientPage struct {
|
||||||
Title string
|
Title string
|
||||||
Host string
|
Host string
|
||||||
|
@ -26,36 +18,43 @@ func main() {
|
||||||
|
|
||||||
app.RegisterView(iris.HTML("./templates", ".html")) // select the html engine to serve templates
|
app.RegisterView(iris.HTML("./templates", ".html")) // select the html engine to serve templates
|
||||||
|
|
||||||
ws := websocket.New(websocket.Config{
|
// Almost all features of neffos are disabled because no custom message can pass
|
||||||
// to enable binary messages (useful for protobuf):
|
// when app expects to accept and send only raw websocket native messages.
|
||||||
// BinaryMessages: true,
|
// When only allow native messages is a fact?
|
||||||
|
// When the registered namespace is just one and it's empty
|
||||||
|
// and contains only one registered event which is the `OnNativeMessage`.
|
||||||
|
// When `Events{...}` is used instead of `Namespaces{ "namespaceName": Events{...}}`
|
||||||
|
// then the namespace is empty "".
|
||||||
|
ws := websocket.New(websocket.DefaultGorillaUpgrader, websocket.Events{
|
||||||
|
websocket.OnNativeMessage: func(nsConn *websocket.NSConn, msg websocket.Message) error {
|
||||||
|
log.Printf("Server got: %s from [%s]", msg.Body, nsConn.Conn.ID())
|
||||||
|
|
||||||
|
nsConn.Conn.Server().Broadcast(nsConn, msg)
|
||||||
|
return nil
|
||||||
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
ws.OnConnect = func(c *websocket.Conn) error {
|
||||||
|
log.Printf("[%s] Connected to server!", c.ID())
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
ws.OnDisconnect = func(c *websocket.Conn) {
|
||||||
|
log.Printf("[%s] Disconnected from server", c.ID())
|
||||||
|
}
|
||||||
|
|
||||||
|
app.HandleDir("/js", "./static/js") // serve our custom javascript code.
|
||||||
|
|
||||||
// register the server on an endpoint.
|
// register the server on an endpoint.
|
||||||
// see the inline javascript code i the websockets.html, this endpoint is used to connect to the server.
|
// see the inline javascript code i the websockets.html, this endpoint is used to connect to the server.
|
||||||
app.Get("/my_endpoint", ws.Handler())
|
app.Get("/my_endpoint", websocket.Handler(ws))
|
||||||
|
|
||||||
app.HandleDir("/js", "./static/js") // serve our custom javascript code
|
|
||||||
|
|
||||||
app.Get("/", func(ctx iris.Context) {
|
app.Get("/", func(ctx iris.Context) {
|
||||||
ctx.ViewData("", clientPage{"Client Page", "localhost:8080"})
|
ctx.View("client.html", clientPage{"Client Page", "localhost:8080"})
|
||||||
ctx.View("client.html")
|
|
||||||
})
|
|
||||||
|
|
||||||
ws.OnConnection(func(c websocket.Connection) {
|
|
||||||
|
|
||||||
c.OnMessage(func(data []byte) {
|
|
||||||
message := string(data)
|
|
||||||
c.To(websocket.Broadcast).EmitMessage([]byte("Message from: " + c.ID() + "-> " + message)) // broadcast to all clients except this
|
|
||||||
c.EmitMessage([]byte("Me: " + message)) // writes to itself
|
|
||||||
})
|
|
||||||
|
|
||||||
c.OnDisconnect(func() {
|
|
||||||
fmt.Printf("\nConnection with ID: %s has been disconnected!", c.ID())
|
|
||||||
})
|
|
||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// Target some browser windows/tabs to http://localhost:8080 and send some messages,
|
||||||
|
// see the static/js/chat.js,
|
||||||
|
// note that the client is using only the browser's native WebSocket API instead of the neffos one.
|
||||||
app.Run(iris.Addr(":8080"))
|
app.Run(iris.Addr(":8080"))
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,11 +1,6 @@
|
||||||
var messageTxt;
|
var messageTxt = document.getElementById("messageTxt");
|
||||||
var messages;
|
var messages = document.getElementById("messages");
|
||||||
|
var sendBtn = document.getElementById("sendBtn")
|
||||||
$(function () {
|
|
||||||
|
|
||||||
messageTxt = $("#messageTxt");
|
|
||||||
messages = $("#messages");
|
|
||||||
|
|
||||||
|
|
||||||
w = new WebSocket("ws://" + HOST + "/my_endpoint");
|
w = new WebSocket("ws://" + HOST + "/my_endpoint");
|
||||||
w.onopen = function () {
|
w.onopen = function () {
|
||||||
|
@ -13,26 +8,28 @@ $(function () {
|
||||||
};
|
};
|
||||||
|
|
||||||
w.onclose = function () {
|
w.onclose = function () {
|
||||||
appendMessage($("<div><center><h3>Disconnected</h3></center></div>"));
|
appendMessage("<div><center><h3>Disconnected</h3></center></div>");
|
||||||
};
|
};
|
||||||
w.onmessage = function (message) {
|
w.onmessage = function (message) {
|
||||||
appendMessage($("<div>" + message.data + "</div>"));
|
appendMessage("<div>" + message.data + "</div>");
|
||||||
};
|
};
|
||||||
|
|
||||||
|
sendBtn.onclick = function () {
|
||||||
|
myText = messageTxt.value;
|
||||||
|
messageTxt.value = "";
|
||||||
|
|
||||||
$("#sendBtn").click(function () {
|
appendMessage("<div style='color: red'> me: " + myText + "</div>");
|
||||||
w.send(messageTxt.val().toString());
|
w.send(myText);
|
||||||
messageTxt.val("");
|
};
|
||||||
|
|
||||||
|
messageTxt.addEventListener("keyup", function (e) {
|
||||||
|
if (e.keyCode === 13) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
|
sendBtn.click();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
})
|
function appendMessage(messageDivHTML) {
|
||||||
|
messages.insertAdjacentHTML('afterbegin', messageDivHTML);
|
||||||
|
|
||||||
function appendMessage(messageDiv) {
|
|
||||||
var theDiv = messages[0];
|
|
||||||
var doScroll = theDiv.scrollTop == theDiv.scrollHeight - theDiv.clientHeight;
|
|
||||||
messageDiv.appendTo(messages);
|
|
||||||
if (doScroll) {
|
|
||||||
theDiv.scrollTop = theDiv.scrollHeight - theDiv.clientHeight;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,17 +4,15 @@
|
||||||
<title>{{ .Title}}</title>
|
<title>{{ .Title}}</title>
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body style="padding:10px;">
|
||||||
<div id="messages"
|
|
||||||
style="border-width: 1px; border-style: solid; height: 400px; width: 375px;">
|
|
||||||
|
|
||||||
</div>
|
|
||||||
<input type="text" id="messageTxt" />
|
<input type="text" id="messageTxt" />
|
||||||
<button type="button" id="sendBtn">Send</button>
|
<button type="button" id="sendBtn">Send</button>
|
||||||
|
<div id="messages" style="width: 375px;margin:10 0 0 0px;border-top: 1px solid black;">
|
||||||
|
</div>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
var HOST = {{.Host }}
|
var HOST = {{.Host }}
|
||||||
</script>
|
</script>
|
||||||
<script src="js/vendor/jquery-2.2.3.min.js" type="text/javascript"></script>
|
|
||||||
<script src="js/chat.js" type="text/javascript"></script>
|
<script src="js/chat.js" type="text/javascript"></script>
|
||||||
</body>
|
</body>
|
||||||
|
|
||||||
|
|
|
@ -2602,11 +2602,11 @@ func (ctx *context) ClientSupportsGzip() bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
var (
|
var (
|
||||||
errClientDoesNotSupportGzip = errors.New("client doesn't supports gzip compression")
|
errClientDoesNotSupportGzip = errors.New("client doesn't support gzip compression")
|
||||||
)
|
)
|
||||||
|
|
||||||
// WriteGzip accepts bytes, which are compressed to gzip format and sent to the client.
|
// WriteGzip accepts bytes, which are compressed to gzip format and sent to the client.
|
||||||
// returns the number of bytes written and an error ( if the client doesn' supports gzip compression)
|
// returns the number of bytes written and an error ( if the client doesn't support gzip compression)
|
||||||
//
|
//
|
||||||
// You may re-use this function in the same handler
|
// You may re-use this function in the same handler
|
||||||
// to write more data many times without any troubles.
|
// to write more data many times without any troubles.
|
||||||
|
@ -2624,7 +2624,7 @@ func (ctx *context) TryWriteGzip(b []byte) (int, error) {
|
||||||
n, err := ctx.WriteGzip(b)
|
n, err := ctx.WriteGzip(b)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
// check if the error came from gzip not allowed and not the writer itself
|
// check if the error came from gzip not allowed and not the writer itself
|
||||||
if _, ok := err.(*errors.Error); ok {
|
if _, ok := err.(errors.Error); ok {
|
||||||
// client didn't supported gzip, write them uncompressed:
|
// client didn't supported gzip, write them uncompressed:
|
||||||
return ctx.writer.Write(b)
|
return ctx.writer.Write(b)
|
||||||
}
|
}
|
||||||
|
|
|
@ -34,7 +34,6 @@ var (
|
||||||
// GobwasDialer is a `Dialer` type for the gobwas/ws subprotocol implementation.
|
// GobwasDialer is a `Dialer` type for the gobwas/ws subprotocol implementation.
|
||||||
// Should be used on `Dial` to create a new client/client-side connection.
|
// Should be used on `Dial` to create a new client/client-side connection.
|
||||||
GobwasDialer = gobwas.Dialer
|
GobwasDialer = gobwas.Dialer
|
||||||
|
|
||||||
// DefaultGorillaDialer is a gorilla/websocket dialer with all fields set to the default values.
|
// DefaultGorillaDialer is a gorilla/websocket dialer with all fields set to the default values.
|
||||||
DefaultGorillaDialer = gorilla.DefaultDialer
|
DefaultGorillaDialer = gorilla.DefaultDialer
|
||||||
// DefaultGobwasDialer is a gobwas/ws dialer with all fields set to the default values.
|
// DefaultGobwasDialer is a gobwas/ws dialer with all fields set to the default values.
|
||||||
|
@ -50,6 +49,14 @@ var (
|
||||||
// See examples for more.
|
// See examples for more.
|
||||||
Dial = neffos.Dial
|
Dial = neffos.Dial
|
||||||
|
|
||||||
|
// IsTryingToReconnect reports whether the "err" is from a client
|
||||||
|
// that was trying to reconnect to the websocket server,
|
||||||
|
// the first output parameter is the number of total reconnection retries,
|
||||||
|
// including the previous failures and the succeed last one.
|
||||||
|
//
|
||||||
|
// Use it on registered callbacks for `Server#OnUpgradeError`.
|
||||||
|
IsTryingToReconnect = neffos.IsTryingToReconnect
|
||||||
|
|
||||||
// OnNamespaceConnect is the event name which its callback is fired right before namespace connect,
|
// OnNamespaceConnect is the event name which its callback is fired right before namespace connect,
|
||||||
// if non-nil error then the remote connection's `Conn.Connect` will fail and send that error text.
|
// if non-nil error then the remote connection's `Conn.Connect` will fail and send that error text.
|
||||||
// Connection is not ready to emit data to the namespace.
|
// Connection is not ready to emit data to the namespace.
|
||||||
|
|
Loading…
Reference in New Issue
Block a user