Initialization & Users

Last Edit: Nov 18 2020

The code below creates a chat client instance for browser/mobile usage. Additional options, such as API base URL and request timeouts, can be provided to the client.Setting.


import { StreamChat } from 'stream-chat';

// client-side you initialize the Chat client with your API key
const client = new StreamChat('YOUR_API_KEY', {
    timeout: 6000,
});
                    

// Typically done in your Application class using your API Key
ChatClient client = new ChatClient.Builder("{{ api_key }}", context).build();

// Static reference to initialised client
ChatClient staticClientRef = ChatClient.instance();
                    

// Import StreamChatClient framework.
import StreamChatClient

// Setup the Stream Chat Client with your API key 
// Preferably in `application(_ application:didFinishLaunchingWithOptions:)`
// This needs to be called only once, since a singleton cannot be configured multiple times!
Client.configureShared(.init(apiKey: "{{ api_key }}"))
// Note: If you want to enable logs for requests and events you can enable them with extra parameter:  `logOptions`.
                    

// Typically done in your Application class using your API Key
val client = ChatClient.Builder("{{ api_key }}", context).build()

// Static reference to initialised client
val staticClientRef = ChatClient.instance()
                    

// client-side you initialize the Chat client with your API key
final client = Client(
  "{{ api_key }}",
  logLevel: Level.INFO,
  connectTimeout: Duration(milliseconds: 6000),
  receiveTimeout: Duration(milliseconds: 6000),
);
                    

Setting the User

Once initialized, you must specify the current user with setUser:


await client.setUser(
    {
        id: 'john',
        name: 'John Doe',
        image: 'https://getstream.io/random_svg/?name=John',
    },
    'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoiamxhaGV5In0.OkDbpbujWJ-XIVHaf00Dnqt3v8Yp_nQ6CGzm-Z4QUVc',
);
                    

User user = new User();
user.setId("user-id");

// extraData allows you to add any custom fields you want to store about your user
HashMap<String, Object> extraData = new HashMap<>();
extraData.put("name", "Bender");
extraData.put("image", "https://bit.ly/321RmWb");
user.setExtraData(extraData);

// You can setup a user token in 2 ways.
// 1. Setup the current user with a JWT token.
String token = "{{ chat_user_token }}";
client.setUser(user, token, new InitConnectionListener() {
    @Override
    public void onSuccess(@NotNull ConnectionData data) {
        User user = data.getUser();
        String connectionId = data.getConnectionId();

        Log.i(TAG, String.format("Connection (%s) established for user %s", connectionId, user));
    }

    @Override
    public void onError(@NotNull ChatError error) {
        Log.e(TAG, String.format("There was an error %s", error, error.getCause()));
    }
});

// 2. Setup the current user with a TokenProvider
TokenProvider tokenProvider = new TokenProvider() {
    @NotNull
    @Override
    public String loadToken() {
        return yourTokenService.getToken(user);
    }
};

client.setUser(user, tokenProvider, new InitConnectionListener() {
    @Override
    public void onSuccess(@NotNull ConnectionData data) {
        User user = data.getUser();
        String connectionId = data.getConnectionId();

        Log.i(TAG, String.format("Connection (%s) established for user %s", connectionId, user));
    }

    @Override
    public void onError(@NotNull ChatError error) {
        Log.e(TAG, String.format("There was an error %s", error, error.getCause()));
    }
});
                    

// Create a user when they login
let userExtraData = UserExtraData(name: "Bender", avatarURL: URL(string: "https://bit.ly/321RmWb")!)
let user = User(id: "bender", extraData: userExtraData)

// You can setup a user token in 2 ways.
// 1. Setup the current user with a JWT token.
Client.shared.set(user: user, token: token) { connection in
  // handle completion
}

// 2. Setup the current user with a token provider closure.
let tokenProvider: TokenProvider = { supplyToken in
    // Make a request here to your backend to generate a valid token for the user.
    YourTokenService.shared.getToken(for: user) { token
        supplyToken(token)
    }
}
Client.shared.set(user: user, tokenProvider: tokenProvider) { result in 
  // handle result
}
                    

val user = User("user-id")

// extraData allows you to add any custom fields you want to store about your user
user.extraData["name"] = "Bender"
user.extraData["image"] = "https://bit.ly/321RmWb"

// You can setup a user token in 2 ways.
// 1. Setup the current user with a JWT token.
val token = "{{ chat_user_token }}"
client.setUser(user, token, object : InitConnectionListener() {
    override fun onSuccess(data: ConnectionData) {
        val user: User = data.user
        val connectionId: String = data.connectionId

        Log.i(TAG, "Connection ($connectionId) established for user $user")
    }

    override fun onError(error: ChatError) {
        Log.e(TAG, "There was an error $error", error.cause)
    }
})

// 2. Setup the current user with a TokenProvider
val tokenProvider = object : TokenProvider {
    // Make a request here to your backend to generate a valid token for the user.
    override fun loadToken(): String = yourTokenService.getToken(user)
}

client.setUser(user, tokenProvider, object : InitConnectionListener() {
    override fun onSuccess(data: ConnectionData) {
        val user: User = data.user
        val connectionId: String = data.connectionId

        Log.i(TAG, "Connection ($connectionId) established for user $user")
    }

    override fun onError(error: ChatError) {
        Log.e(TAG, "There was an error $error", error.cause)
    }
})
                    

final user = User(id: "john", extraData: {
  "name": "John Doe",
  "image": "<a href="https://getstream.io/random_svg/?name=John" target="_self">https://i.imgur.com/fR9Jz14.png</a>",
});

await client.setUser(user, "{{ chat_user_token }}");
                    

Note how we are waiting for the setUser API call to be completed before moving forward. You should always make sure to have the user set before making any more calls. All SDKs make this very easy and wait or queue requests until then.

Set User Parameters

Name Type Description Default Optional
user object The user object. Must have id field. It can have as many custom fields as you want, as long as the total size of the object is less than 5KB
userToken string The user authentication token. See Tokens & Authentication for details default

WebSocket Connections

The setUser (or SDK equivalent) function performs several operations when used

  1. Creates a new user if the user_id is not already registered with the application, incrementing the monthly active users

  2. Updates the user in the application (will add/modify existing fields but will not overwrite/delete previously set fields unless the key is used)

  3. Opens a WebSocket connection and increments the Concurrent Connections for the application

The React, React-native, iOS, Android, and Flutter SDK's handle WebSocket disconnection logic, but if a manual disconnect is required in your application, then there are the following options


await chatClient.disconnect();
                    

Client.shared.disconnect()
                    

client.disconnect()
                    

ChatClient.instance().disconnect();
                    

ChatClient.instance().disconnect()