This blog Uncle Cat's Blog For reprinting, please state your origin
Read this article for about "8 minutes"
Readable crowd: Java beginner
Preface
InChat = Iot Netty Chat
First of all, thank you for your support. InChat Friends, you may be working for reasons, or your own ideas, or your own projects and so on.
InChat is not yet a qualified framework. It has many drawbacks and problems, but thank you for your attention and for letting it learn to grow.
Once again, InChat: a lightweight, efficient, multi-terminal (application and hardware Iot) distributed, asynchronous network application communication framework.
InChat stopped updating since January 1.1.3, and for personal reasons (I'm not sure about its consistency in the future). On August 22, InChat released version 1.1.4, and is expected to continue releasing version 1.1.5 in September (because 1.1.4 found some core problems).
Next, I will introduce some basic functions of version 1.1.4 in detail. Welcome to test them, and Here Put forward your opinions or questions.
InChat version
<dependency> <groupId>com.github.UncleCatMySelf</groupId> <artifactId>InChat</artifactId> <version>1.1.4</version> </dependency>
Building SpringBoot's web Project
Because many friends asked about the use of InChat in SpringBook and other web frameworks during the suspension period, this Demo was built entirely in SpringBook environment.
Download address: InChat-SpringBoot-Demo The demo-inchat-4.zip file in the project
Here we suggest that you can knock directly once to see what's wrong.
First, my project is SpringBoot-Web, my database is MySQL, and I don't use Redis.
pom file
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.1.7.RELEASE</version> <relativePath/> <!-- lookup parent from repository --> </parent> <groupId>com.example</groupId> <artifactId>demo-inchat-4</artifactId> <version>0.0.1-SNAPSHOT</version> <name>demo-inchat-4</name> <description>Demo project for Spring Boot</description> <properties> <java.version>1.8</java.version> </properties> <dependencies> <dependency> <groupId>com.github.UncleCatMySelf</groupId> <artifactId>InChat</artifactId> <version>1.1.4</version> <exclusions> <exclusion> <groupId>org.slf4j</groupId> <artifactId>slf4j-log4j12</artifactId> </exclusion> <exclusion> <groupId>log4j</groupId> <artifactId>log4j</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-jpa</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-jdbc</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <scope>runtime</scope> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <optional>true</optional> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project>
With regard to pom files, it should be noted that the InChat version actually comes with log4j, so it may conflict with other log components and need to be removed, which will also be removed in version 1.1.5.
If you use InChat Period Report:
Exception in thread "main" java.lang.IllegalArgumentException: LoggerFactory is not a Logback LoggerContext but Logback is on the classpath.
The corresponding log components can be removed according to the above.
Account login
Basic data relationships
- Message Chat Message Class
@Entity @Data @DynamicUpdate public class Message { /**id,Self increment*/ @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Integer id; /** Message time */ private Date time; /** Message type (to oneself, to friends, to groups) */ private String type; /** Message value (chat content) */ private String value; /** User ID (login token) */ private String token; /** Group chat Id */ private String groudId; /** Whether Online - Individual (Friends Are Online) */ private String online; /** Whether or not to chat online (offline friends) */ private String onlineGroup; /** Message Receiver ID (Receiving Friend Token) */ private String one; }
- User user login (simple simulation)
public class User { /**id*/ @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Integer id; private String username; private String password; }
JPA
Here is a simple JPA processing, like to use MyBatis friends can also try, welcome to contribute Demo
Startup class
Why suddenly talk about boot classes?
Because InChat (all started classes before 1.1.3), this may be a misunderstanding. In this Demo, our start classes are like this.
@SpringBootApplication @EnableScheduling public class DemoInchat4Application { public static void main(String[] args) { SpringApplication.run(DemoInchat4Application.class, args); } }
Yes, that's it. In my business, I didn't plan to start InChat at the beginning. Of course, it depends on the business.
Controller layer
Here Controller is a general way to start the http interface and start the default InChat service.
@RestController public class UserController { @Autowired private UserRepository repository; @GetMapping("/init") public String init(){ ConfigFactory.initNetty = new MyInit(); ConfigFactory.fromServerService = FromServerServiceImpl.TYPE2; ConfigFactory.listenAsynData = new UserListenAsynData(); ConfigFactory.inChatVerifyService = new VerifyServiceImpl(repository); InitServer.open(); return "success"; } }
As you will see, I started InChat through an http and injected a User Repository into InChat's validation class.
Start.
2019-08-23 17:10:52.399 INFO 20136 - [BOSS_1] c.g.u.bootstrap.Netty Bootstrap Server: Server Start Successfully [192.168.1.121:8070]
Next, I will introduce some configuration classes of InChat.
InChat Configuration Class - InitNetty
InitNetty Inheritance
It's the basic configuration for initializing Netty, and you can modify the configuration to suit your needs.
public class MyInit extends InitNetty { @Override public int getWebport() { return 8070; } //Distributed @Override public Boolean getDistributed() { return false; } //encryption @Override public boolean isSsl() { return false; }
InChat Configuration Class - FromServerService
Implementing FromServer Service
This is not different from InChat version 1.1.3. It's a system notification sent by a server that can send tasks through Http.
public enum FromServerServiceImpl implements FromServerService { TYPE1(1,"[System Notice] There is an exception in your account. Please pay attention to the security and confidentiality information."), TYPE2(2,"[Congratulations on your continuous login for more than 5 days, rewarding you with 5 points."); private Integer code; private String message; FromServerServiceImpl(Integer code, String message){ this.code = code; this.message = message; } public Integer getCode() { return code; } public String findByCode(Object code) { Integer codes = (Integer)code; for (FromServerServiceImpl item: FromServerServiceImpl.values()) { if (item.code == codes){ return item.message; } } return null; } public void setCode(Integer code) { this.code = code; } public String getMessage() { return message; } public void setMessage(String message) { this.message = message; } }
InChat configuration class -- ListenAsynData
Inheriting ListenAsynData
Asynchronous data acquisition is the class of chat data acquisition. In 1.1.4, you need to write a carrier (Map or list) to store chat data. In this Demo, I use Map, in fact, I can use list. It should be noted that InChat provides a tool class, Message ChangeUtil, which converts Map into InChat Message.
I hope my business doesn't store data all the time, so I store chat data in Map, use timer, and store it in database regularly.
public class UserListenAsynData extends ListenAsynData { @Override public void asynData(Map<String, Object> maps) { InChatMessage inChatMessage = MessageChangeUtil.Change(maps); CacheMap.add(inChatMessage); } }
InChat Configuration Class - InChatVerifyService
Inheritance of InChat VerifyService
You need to add a static variable to this class to facilitate data manipulation after subsequent initialization.
Two methods in this class are user login checking and group chat member array acquisition based on group chat ID.
These two data are processed by default through the database, group chat ID I am a direct simulation, you can try to store a corresponding table in the database.
public class VerifyServiceImpl implements InChatVerifyService { private UserRepository repository; public VerifyServiceImpl(UserRepository repository){ this.repository = repository; } public boolean verifyToken(String token) { User user = repository.findByUsername(token); if (user.getId() != null){ return true; } return false; } public JSONArray getArrayByGroupId(String groupId) { JSONArray jsonArray = JSONArray.parseArray("[\"1111\",\"2222\",\"3333\"]"); return jsonArray; } }
Timing tasks
I use timed tasks to store chat data regularly. Here's what I need to pay attention to. Make sure that I empty the stored content.
@Component public class SchedulerTask { @Autowired private MessageRepository repository; private static final SimpleDateFormat dateFormat = new SimpleDateFormat("HH:mm:ss"); @Scheduled(fixedRate = 30000) public void reportCurrentTime() { System.out.println("Now time:" + dateFormat.format(new Date())); Map<Integer,InChatMessage> Chatcache = CacheMap.copy(); InChatMessage inChatMessage = Chatcache.get(1); Message message = new Message(); message.setOne(inChatMessage.getOne()); message.setGroudId(inChatMessage.getGroudId()); message.setOnline(inChatMessage.getOnline()); message.setOnlineGroup(inChatMessage.getOnlineGroup()); message.setToken(inChatMessage.getToken()); message.setType(inChatMessage.getType()); message.setValue(inChatMessage.getValue()); message.setTime(inChatMessage.getTime()); repository.save(message); } }
I'll just have a brief idea.
functional testing
In stand-alone mode, send to oneself, others and groups (stand-alone, not encrypted)
Normal operation, due to data storage, I only store one timer, you remember to modify the following
Single machine, ssl encryption, send to oneself, send to others, send to groups (single machine, encryption)
For encryption, you can build your own encryption file, or use inchat.jks
You can refer to it. Instructions for InChat V1.1.3
Generate your own jks encryption file, please make corresponding modifications in the inheritance class of InitNetty class.
public abstract class InitNetty { //... /** Whether to Start Distributed */ private Boolean isDistributed = false; /** Whether to start encryption */ private boolean ssl = false; private String jksFile = "inchat.jks"; private String jksStorePassword = "123456"; private String jksCertificatePassword = "123456"; //.... }
Distributed, sending data
This Demo is not tested yet, but you are interested in it. Instructions for InChat V1.1.3 Learn to understand.
Because both Demo projects will have data storage after distributed use, which is not within the design scope of InChat, it is recommended that you use the stand-alone version first.
Follow-up distributed, there will be a data storage mid-cloud component, centralized processing of chat data storage issues, and so on.
InChat will continue to grow.
Public Number: Java Cat Says
Learning Communication Group: 728698035
Architecture design (code farmer) and entrepreneurship technical consultant, uninhibited mediocrity, love open source, chat about the process of life and irregular dry goods.