
📘Introduction |📽Video Demo | 🏖TODO LIST | 🌈Architecture |💡Flow Chart|🌁Quick Start|👨🏻✈️Built-in Commands|🎤Chat|❓QA|💌Contact
中文文档
V2.0
Introduction
CIM(CROSS-IM) is an IM (instant messaging) system for developers; it also provides some components to help developers build their own scalable IM.
Using CIM, you can achieve the following requirements:
IM instant messaging system.
- Message push middleware for
APP.
- Message middleware for
IOT massive connection scenarios.
If you have any questions during use or development, you can contact the author.
Video Demo
Click the links below to watch the video demo.
| YouTube | Bilibili |
|---|
| Group Chat Private Chat | Group Chat Private Chat |
 |  |

TODO LIST
Architecture

- Each component in
CIM is built using SpringBoot
- Client build with cim-client-sdk
- Use
Netty to build the underlying communication.
MetaStore is used for registration and discovery of IM-server services.
cim-server
IM server is used to receive client connections, message forwarding, message push, etc.
Support cluster deployment.
cim-route
Route server; used to process message routing, message forwarding, user login, user offline, and some operation tools (get the number of online users, etc.).
cim-client
IM client terminal, a command can be started and initiated to communicate with others (group chat, private chat).
Flow Chart

- Server register to
MetaStore
- Route subscribe
MetaStore
- Client login to Route
- Route get Server info from
MetaStore
- Client open connection to Server
- Client1 send message to Route
- Route select Server and forward message to Server
- Server push message to Client2
Quick Start
Docker
The allin1 image comes with Zookeeper, Redis, cim-server, and cim-forward-route pre-installed, all managed by Supervisor for an out-of-the-box experience.
Supported platforms: linux/amd64, linux/arm64, linux/arm/v7
Port mapping:
| Port | Service | Description |
|---|
| 2181 | Zookeeper | Service registration & discovery |
| 6379 | Redis | Data caching |
| 8083 | Route Server | HTTP API routing service |
Pull the image and start the container:
docker pull ghcr.io/crossoverjie/allin1-ubuntu:latest
docker run -p 2181:2181 -p 6379:6379 -p 8083:8083 --rm --name cim-allin1 ghcr.io/crossoverjie/allin1-ubuntu:latest
After the container starts, refer to the Register Account and Start Client sections below to experience the full IM workflow.
Build Docker Image Locally
To build the Docker image from source:
# Run from the project root directory
docker build -t cim-allin1:latest -f docker/allin1-ubuntu.Dockerfile .
docker run -p 2181:2181 -p 6379:6379 -p 8083:8083 --rm --name cim-allin1 cim-allin1:latest
Build from Source
First, install Zookeeper and Redis and ensure the network is accessible.
docker run --rm --name zookeeper -d -p 2181:2181 zookeeper:3.9.2
docker run --rm --name redis -d -p 6379:6379 redis:7.4.0
git clone https://github.com/crossoverJie/cim.git
cd cim
mvn clean install -DskipTests=true
cd cim-server && cim-client && cim-forward-route
mvn clean package spring-boot:repackage -DskipTests=true
Deploy IM-server (cim-server)
cp /cim/cim-server/target/cim-server-1.0.0-SNAPSHOT.jar /xx/work/server0/
cd /xx/work/server0/
nohup java -jar /root/work/server0/cim-server-1.0.0-SNAPSHOT.jar --cim.server.port=9000 --app.zk.addr=<zk-address> > /root/work/server0/log.file 2>&1 &
For cim-server cluster deployment, just ensure all instances point to the same Zookeeper address.
Deploy Route Server (cim-forward-route)
cp /cim/cim-server/cim-forward-route/target/cim-forward-route-1.0.0-SNAPSHOT.jar /xx/work/route0/
cd /xx/work/route0/
nohup java -jar /root/work/route0/cim-forward-route-1.0.0-SNAPSHOT.jar --app.zk.addr=<zk-address> --spring.redis.host=<redis-address> --spring.redis.port=6379 > /root/work/route/log.file 2>&1 &
cim-forward-route is stateless and can be deployed on multiple nodes; use Nginx as a reverse proxy.
Start Client
cp /cim/cim-client/target/cim-client-1.0.0-SNAPSHOT.jar /xx/work/route0/
cd /xx/work/route0/
java -jar cim-client-1.0.0-SNAPSHOT.jar --server.port=8084 --cim.user.id=<unique-client-id> --cim.user.userName=<username> --cim.route.url=http://<route-server>:8083/

As shown above, two clients can communicate with each other.
Local Client Startup
Register Account
curl -X POST --header 'Content-Type: application/json' --header 'Accept: application/json' -d '{
"reqNo": "1234567890",
"timeStamp": 0,
"userName": "zhangsan"
}' 'http://<route-server>:8083/registerAccount'
Get the userId from the response:
{
"code":"9000",
"message":"success",
"reqNo":null,
"dataBody":{
"userId":1547028929407,
"userName":"test"
}
}
Start Local Client
# Start local client
cp /cim/cim-client/target/cim-client-1.0.0-SNAPSHOT.jar /xx/work/route0/
cd /xx/work/route0/
java -jar cim-client-1.0.0-SNAPSHOT.jar --server.port=8084 --cim.user.id=<userId-from-above> --cim.user.userName=<username> --cim.route.url=http://<route-server>:8083/
Built-in Commands
| Command | Description |
|---|
:q! | Quit the client |
:olu | List all online users |
:all | Show all available commands |
:q [keyword] | Search chat history by keyword |
:ai | Enable AI mode |
:qai | Disable AI mode |
:pu | Fuzzy search users |
:info | Show client information |
:emoji [option] | Browse emoji list [option: page number] |
:delay [msg] [delayTime] | Send a delayed message |
: | More commands are under development... |

Chat History Query

Use the command :q keyword to search chat history related to you.
Client chat history is stored in /opt/logs/cim/ by default, so write permission is required for this directory. You can also customize the directory by adding --cim.msg.logger.path=/custom/path to the startup command.
AI Mode

Use the command :ai to enable AI mode. After that, all messages will be responded to by AI.
Use :qai to exit AI mode.
Prefix Match Username

Use the command :qu prefix to search user information by prefix.
This feature is primarily designed for searching users in input fields on mobile clients.
Group Chat/Private Chat
Group Chat

For group chat, simply type a message in the console and press Enter to send. All online clients will receive the message.
Private Chat
To send a private message, you need to know the recipient's userID.
Use the command :olu to list all online users.

Then use the format userId;;message content to send a private message.

Meanwhile, the other account will not receive the message.

Emoji Support
Use the command :emoji 1 to list all available emojis. Use the emoji alias to send an emoji.

Delayed Messages
Send a message with a 10-second delay:
:delay delayMsg 10

Contact
Contributing
We welcome contributions! Before submitting a PR, please ensure your code passes the Checkstyle check.
Code Style
This project uses Checkstyle to enforce code style. The rules are defined in checkstyle/checkstyle.xml.
Run Checkstyle locally before committing:
mvn checkstyle:check
Key rules:
- Use spaces around
{, }, and operators
- No trailing whitespace
- Files must end with a newline
- Remove unused imports
- Constants (
static final) must be UPPER_SNAKE_CASE
- Use Java-style array declarations:
String[] args (not String args[])
Skip Checkstyle for quick builds:
mvn package -Dcheckstyle.skip=true