Giter VIP home page Giter VIP logo

webwire-go's Issues

Autoconnect in the background

Issue #11 already covers the autoconnect feature but misses one important case:

When the client connects to the server just to listen to server-side signals - the connection could get lost at some point (due to a server reboot for example) and the user-code will assume, that there's just nothing happening on the server, but in reality the server just won't send the signals due to the client being disconnected whole the time.
In such a case it's very important for the client to try to reconnect in the background as soon as the connection is lost to ensure maximum uptime.

Support multiple underlying websocket connections

Client Feature Request

Proposed Behavior

The client should provide an option for multiple underlying connections to be used for potentially increased throughput and lower latencies in network environments with high packet loss. Messages should be distributed fan-out round-robin on the available connections.
Ideally, the number of underlying connections should be dynamically adjustable.

Actual Behavior

The webwire client currently utilizes just one single websocket connection. In network environments where packet loss is small having an HTTP/2-style multiplexed single TCP/IP connection (which the underlying WebSocket basically is) is ideal, though in network environments with high packet loss HTTP/1.1-style multiple individual TCP/IP connections should, in theory, provide better throughput and latency due to the TCP congestion-avoidance algorithm, which could potentially cause artificial slowdowns resulting in unsaturated network usage, at the cost of memory usage and higher connection establishment latency.

Proposed API

To be discussed

Proposed Implementation

To be discussed

Additional information

The server must also support this feature by providing an option of a maximum number of acceptable connections for a single client, though I'm not quite sure whether this is the case.

Multi-Connection Session

Problem

Currently a session can only be assigned to a single connection, though sessions should accept multiple simultaneous connections to support authentication across multiple browser tabs/windows of the same domain.

Proposed Solution

Ease this restriction by adding an option for the maximum number of simultaneous connections associatable with a single session.

Request delivery order

Currently, requests performed one after the other will arrive at the server in serial order, though the order is broken when in the meanwhile the server is unavailable and the client is trying to reconnect before sending out accumulated requests. I suggest making the client retain the order the requests were initially made in to avoid unsynchronized delivery.

Add new constructor function with TLS support

Server feature request

Description

For use webwire on https we need to do a lot of action, as in example. It will be more convenient to have a constructor that will accept, in addition to the ServerImplementation and ServerOptions, a certificate with a key and listen https connections, like:

func NewSecureServer(
	implementation ServerImplementation,
	opts ServerOptions,
	certFile,
	keyFile string,
)

Unsynchronized session getter

The client agent method client.Session() should return a copy of the session object though there is a problem with it returning a shallow copy of the session info map. This could lead to unsychronized access to the session info map as both session objects reference the same info object but can be owned by different goroutines.

TLS handshake error doesn't stop autoconnect

Bug Report

Expected Behavior

In the case of TLS handshake errors (such as a certificate verification error due to untrusted authority on a self-signed certificate), the client must immediately return an error aborting the automatic connection establishment process.

Actual Behavior

The automatic connection establishment process enters an infinite loop trying to connect indefinitely.

Reproduction Steps

  • Launch the chatroom example server with the provided self-signed certificate.
  • Launch the chatroom example client setting InsecureSkipVerify to false in the TLS configuration and watch it trying to connect indefinitely.

Environment

Subprotocol Support

Generic Issue

Add support for custom subprotocols. Currently, sub-protocols have to be implemented using the namespacing feature, where different types of requests/signals have different names, which is fine so far but webwire doesn't distinguish between different subprotocols at all, it should at least avoid connecting to a webwire server that doesn't speak it's language.

Allow custom session key generators

Currently, there's no way to implement your own session key generator which is rather restrictive. It'd be nice to have the possibility to provide your own generator or use the built-in generator by default.

Default session storage

Currently sessions are silently disabled if one of the sessions related hooks is undefined which is rather unintuitive. Consider adding a default built-in session storage implementation to be used by default if all sessions related hooks are undefined. This would improve usability and help newcomers getting started faster.

Support for concurrent message processing

Currently the server does handle multiple connections concurrently but it processes the messages sequentially. Requests and signals of a single client are always processed in the goroutine handling that particular client, this could turn out critical, because even if we spawn goroutines manually in the OnRequest handler for example - we'd still block other requests when waiting for the blocking one to return a response. It'd therefore make sense to move the processing of messages into separate goroutines and ideally make this feature optional by providing a server option for disabling concurrent message processing.

Concurrent access to client session causes data race

Problem

Concurrent access to the session object in the client by both the reading goroutine created during the connection setup and the writing goroutine calling the API (when calling the client.RestoreSession method for example) causes a data race!

Proposed Solution

Synchronize read-write access to the internal client session object.

Graceful Shutdown

The webwire server should keep track of currently processed requests and signals and wait for them to finish before closing to avoid data loss and errors. During a requested shutdown new connections, requests and signals must not be accepted.

Listing all connections of a session

There's currently no way to list all connections (aka client agents) belonging to a certain session. The only function that comes close to solving this issue is SessionRegistry.SessionConnections though it returns only the number of connections of the given session. Wouldn't it make more sense to return []*Client instead?

Deferred client agent closure

Calling client.Close() on a client agent while processing it's request causes an internal server error, because the response cannot be sent due to the client being disconnected immediately.

client.Close() must defer closing the client agent until all work on that client agent is finished.

Use *log.Logger instead of io.Writer for logging

Use *log.Logger instead of io.Writer for logging, it allows the library user to set custom logging flags and prefixes. Currently this is not possible and the default prefixes are used like: WARNING: and ERROR: , though we'd like to differentiate between error logs produced by webwire and our own code.

Update session relevance

Sessions must get a new field "lastUse" of date type to indicate when a particular session was lastly updated. This is important for the session manager to know whether a session is still relevant during garbage collection.

Auto-connect and auto-reconnect

Make the webwire client automatically connect to the server right after initialization and make it optionally automatically reconnect on connection loss

Duplex Request-Reply

Currently the request-reply topology works in a single direction: client -> server which is fine for now, but shouldn't we consider adding support for duplex request-reply to also be able to send requests from the server to the client?

Use standard error interface in OnRequest hook

Currently a custom error type webwire.Error is used in the OnRequest hook, which is fine but consider using the default Go error interface as this would ease the use of the library. When a non-webwire.Error is returned the transmitted reply error could probably have some default code value.

Support for JSON message encoding

Currently only UTF8 and UTF16 text as well as plain binary messages are supported, so theoretically native support for JSON could prove handy.

Deferred client-side session destruction

When the session is closed by the client offline due a temporarily interrupted connection, then the client will just remove and forget it while it will remain open on the server even when the connection is reestablished.

The client should be made responsible for cleaning up when a session was closed offline. It must remember the session key and request the destruction of the closed sessions as soon as the connection is reestablished, to reduce server-load.

Request message requires a payload

Request message requires a payload even though a payload shouldn't be obligatory. In some cases a request name is sufficient. For example if we just want to notify the server about an event like client.Request("event_a_happend", wwr.Payload{}) then we won't need a payload, but currently we have to provide a payload otherwise an error is returned indicating that the request message couldn't be parsed.

WEBWIRE_ERR: 2018/05/15 18:26:36 serverHttp.go:72: Failed parsing message: Invalid request message, too short

Limit concurrency per client

As of #23 the maximum number of concurrently executed handlers can be limited globally affecting all connected clients, though it might make sense to also allow limiting the number of concurrently executed handlers per client as well.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.