How to send messages to a AWS websocket custom route in flutter

Viewed 246

I've set up a websocket in AWS using API gateway and a simple lambda function shown below:

import json
import boto3

def lambda_handler(event, context):
    route = event["requestContext"]["routeKey"]
    connectionId = event["requestContext"]["connectionId"]
    
    client = boto3.client('apigatewaymanagementapi',
                endpoint_url='https://testid.execute-api.ap-southeast-2.amazonaws.com/production')
    
    if route == "$connect":
        print('Connection occured')
       
        
    elif route == "$disconnect":
        print("Disconnected")
        
    elif route == "message":
        print("Message received")
        api = client.post_to_connection(
            Data=json.dumps({'result': 'success'}),
            ConnectionId = connectionId
        )
        
    return {
        'statusCode': 200,
        'body': json.dumps('Hello from Lambda!')
    }

In flutter I connect to the websocket on startup using the web_socket_channel package (skipped some boilerplate code for simplicity)

import 'package:web_socket_channel/io.dart';

@override
void initState() {
super.initState();

WidgetsBinding.instance?.addPostFrameCallback((_) async {
  channel = IOWebSocketChannel.connect('wss://testid.execute-api.ap-southeast-2.amazonaws.com/production');

  channel.stream.listen((message) {
    print(message);
  });
  }
}

When I check the AWS lambda logs I can see that a connection was definitely established. I then use a button to trigger a function that sends a message to the message route.

 void sendMessage(){
      channel.sink.add({'action':'message'});
  }

On running the sendMessage function, nothing happens and the connection gets disconnected. I'm actually not sure if that's the way to send a message to a custom route as I couldn't find anything in the docs for the web_socket_channel package. How can I get this working so that the connection stays alive and receives messages from the lambda?

1 Answers

Oh solved it. I just needed to send the json as a string.

void sendMessage(){
      channel.sink.add(jsonEncode({'action':'message'}));
  }
Related