Giter Site home page Giter Site logo

benlodotcom / blwebsocketsserver Goto Github PK

View Code? Open in Web Editor NEW
158.0 11.0 36.0 432 KB

BLWebSocketsServer is a lightweight websockets server for iOS built around libwebsockets. The server suports both synchronous requests and push.

License: MIT License

Ruby 0.23% Objective-C 7.02% C 92.74%

blwebsocketsserver's Introduction

Build Status

BLWebSocketsServer is a lightweight websockets server for iOS built around libwebsockets. The server suports both synchronous requests and push.

Here's how easy it is to start a Websockets server in your iOS app:

//every request made by a client will trigger the execution of this block.
[[BLWebSocketsServer sharedInstance] setHandleRequestBlock:^NSData *(NSData *data) {
  //simply echo what has been received
  return data;
}];
//Start the server
[[BLWebSocketsServer sharedInstance] startListeningOnPort:9000 withProtocolName:@"my-protocol-name" andCompletionBlock:^(NSError *error) {
    if (!error) {
        NSLog(@"Server started");
    }
    else {
        NSLog(@"%@", error);
    }
}];
//Push a message to every connected clients
[[BLWebSocketsServer sharedInstance] pushToAll:[@"pushed message" dataUsingEncoding:NSUTF8StringEncoding]];

Installation

From CocoaPods

Add pod 'BLWebSocketsServer' to your Podfile or pod 'BLWebSocketsServer', :head if you're feeling adventurous.

Manually

Important note if your project doesn't use ARC: you must add the -fobjc-arc compiler flag to BLWebSocketsServer.m in Target Settings > Build Phases > Compile Sources.

  • Copy the BLWebSocketsServer folder into your project.
  • Add libz.dylib.
  • Import BLWebSocketsServer.h

Usage

See the sample Xcode project for an example of implementation with both synchronous and asynchronous messaging.

Reference

//Access the BLWebSocketsServer singleton
[BLWebSocketsServer sharedInstance]
//To handle a request, use a block that receives as arguments the data in the request and returns the response data
typedef NSData *(^BLWebSocketsHandleRequestBlock)(NSData * requestData);
//Add the block that'll handle the request and the corresponding response with this
- (void)setHandleRequestBlock:(BLWebSocketsHandleRequestBlock)block;
//Method to start the server
- (void)startListeningOnPort:(int)port withProtocolName:(NSString *)protocolName andCompletionBlock:(void(^)(NSError *error))completionBlock;
//Get the status of the server with this
@property (atomic, assign, readonly) BOOL isRunning;
//Push data to all the connected clients
- (void)pushToAll:(NSData *)data;
//Well...method to stop the server
- (void)stopWithCompletionBlock:(void(^)())completionBlock;

Contribute

When there is a change you'd like to make (if you don't feel inspired you can check the Todo below):

Todo

  • Add the ability to listen simultaneously on multiple ports for different protocols.
  • Use dispatch sources instead of an infinite loop.
  • Add a session store.
  • Implement per user push.

Keep working on the documentation, it is a never ending task anyway ;-)

Contact

Benjamin Loulier

License

BLWebSocketsServer is available under the MIT license. See the LICENSE file for more info.

blwebsocketsserver's People

Contributors

benlodotcom avatar ku avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

blwebsocketsserver's Issues

Safari closes connection on large messages with x-webkit-deflate-frame

I noticed today that sending large messages (e.g. 100.000 bytes) to a BLWebSocketsServer from a Safari browser (either iOS or Desktop) causes a close on the connection.

This behaviour does not happen with other browsers (e.g. Chrome) and stops immediately once I comment out the x-webkit-deflate-frame extension in extension.c. I am not really a websocket expert and unsure if this is an issue with BLWebSocketsServer or with libwebsocket.

To test, you can create a simple echo server and then use this code (with adjusted IP and PORT):

<html>
<body>
<script>

function log(msg) {
  document.getElementsByTagName("body")[0].innerHTML += msg+"<br/>";
}

var websocket       = new WebSocket("ws://IP:PORT");
websocket.onopen    = function() {
  log("Open");

    var x = "";
    for( var i=0; i < 100000; i++ )
        x += "x";
    log("Sending "+x.length+" bytes.");
    websocket.send(x);
};
websocket.onclose   = function(e) {
  log("Close ("+e.code+")");
};

</script>
</html>

The result in Chrome is:

Open
Sending 100000 bytes.

The result in Safari is:

Open
Sending 100000 bytes.
Close (1006)

-pushToAll sends dual messages

I've got BLWebSocketsServer set up normally and I have one "client" connected to the server. I'm encoding an NSString as NSData and then using the -pushToAll: method to simply send that string to the client on the other side of the socket. The client simply runs an 'alert()' to display the sent message.

The trouble is that every time I send a message, the client receives it TWICE. So I stuck an NSLog statement in this section of BLWebSocketsServer.m:

case LWS_CALLBACK_SERVER_WRITEABLE: {
    NSData *message = [sharedInstance.asyncMessageQueue messageForUserWithId:*session_id];
    NSLog(@"Writing: %@", [[NSString alloc] initWithData:message encoding:NSUTF8StringEncoding]);

    write_data_websockets(message, wsi);
    break;
    }

And sure enough, I see two "Writing: ..." messages in my log every time I call -pushToAll once. (I have a log statement in that method as well, verifying that it is called only once.)

Any advice on how to combat this? I have a feeling something is mixed up with the enqueue/dequeue stuff so that the messageCount is off, or the messages aren't properly removed.

Value conversion issues

This picks up where #6 left off.

When building my project I receive 28 warnings stating that Implicit conversion loses integer precision.

All but one of the implicit conversion warnings originate from libwebsockets.

The other is coming from BLAsyncMessageQueue.m:

screen shot 2014-08-30 at 02 55 53

compile error

I created a new project and follow the steps in the readme.md.
then got error messages:

image

And if I give a line code: "#define HAVE_GETIFADDRS 1", the errors gone, but I don't know if this is the best resolution.

10.9 Compatibility

Hi Ben,

I talked with an Apple Engineer today about the effects that the new App Nap API will have on background apps in 10.9. Essentially, the system is going to "intelligently" throttle the resources available to apps that are in the background so that they are de-prioritized on the CPU.

According to this engineer, this will primarily affect NSTimers and polling operations. The reason I bring this up is that BLWebSocketsServer uses polling. Given that 10.9 is going to drop the hammer on apps that use polling, I figured it would be a good time to get this library off of it, if possible.

I understand your class pretty well, but I'm not familiar with libwebsockets and the associated API. So forgive me if this is a dumb question, but why is the polling necessary? You're just checking to see if "messagesCount" is greater than 0, then calling down to libwebsockets. Why not use KVO to simply observe changes to the "messagesCount" property? When it changes, check it, if it's greater than 0, fire the call to libwebsockets. Alternately, have the -enqueueMessage methods trigger a call to libwebsockets once they complete.

I thought of modifying your code to try this, but then I figured you must have had a good reason to fall back on polling, so I'm probably missing some idiosyncrasy with libsockets.

Last socket connected does not work

Hi Ben,

I've integrated BLWebSocketsServer into a Cocoa app on Mac OS 10.8.4. When I use the -pushToAll: method, it fails to work for the most recently added socket. So, when I have only one client socket open, it does not work. But as soon as I open a second client socket (say, by loading the HTML page, which I'm serving locally over Mamp) the first socket client starts receiving the messages. Then, if I add a 3rd client (by opening the same html page on my iPad), both the first two clients start receiving messages but the most recent socket (the iPad) does not.

I'm wondering if this is a bug, or if I'm doing something wrong.

Have you modified the official source code of libwebsockets ?

Hello, @benlodotcom

I'm going to build https://github.com/warmcat/libwebsockets to a static lib for ios platform, but failed.

I found that BLWebSocketsServer has used libwebsockets too.
And i have found that you modified the source code of libwebsockets , e.g. Libwebsockets-master/Lib/Libwebsockets.h and Libwebsockets-master/Lib/Private-libwebsockets.h. Becourse the official files include "lws_config.h" which is generated by config.h.in, and i cann't generate it easily.

So, how do you know what to modified ?
Thank you!

Testing on iOS 5.x

I'm wrapping libwebsockets for my project, then I found your wrapper, it seems that you haven't tested on iOS 5.x.

Latest libwebsockets doesn't support iOS 5.x since UIWebView on iOS 5.x is using an older draft which libwebsockets has deprecated.

Web service closed

Web server will close When the app enter background. So I want keep it alive in background unless user force close. What should I do?

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.