package com.its.pis.xnetudp;

import com.its.app.AppUtils;
import com.its.pis.config.ProcessConfig;
import com.its.pis.xnetudp.codec.CenterCommServerDecoder;
import com.its.pis.xnetudp.handler.CenterCommServerPacketHandler;
import io.netty.bootstrap.Bootstrap;
import io.netty.channel.Channel;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelOption;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioDatagramChannel;
import lombok.ToString;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;

import javax.annotation.PostConstruct;

@Slf4j
@ToString
@Component
public class UdpServerCenterComm extends UdpServerAbstract {

    private ProcessConfig processConfig;

    @PostConstruct
    private void init() {
        this.processConfig = (ProcessConfig) AppUtils.getBean(ProcessConfig.class);
    }
    public void run() {
        log.info("UdpServerCenterComm.init: Start.");

        try {
            this.nioEventLoopGroup = new NioEventLoopGroup();
            this.bootstrap = new Bootstrap();
            this.bootstrap.channel(NioDatagramChannel.class);
            this.bootstrap.group(this.nioEventLoopGroup);
            this.bootstrap.option(ChannelOption.SO_BROADCAST, Boolean.valueOf(true));
            //this.bootstrap.option(ChannelOption.SO_RCVBUF, Integer.valueOf(655350));
            //this.bootstrap.option(ChannelOption.SO_SNDBUF, Integer.valueOf(655350));
            this.bootstrap.option(ChannelOption.SO_REUSEADDR, Boolean.valueOf(true));
            this.bootstrap.handler(new ChannelInitializer<Channel>() {
                @Override
                protected void initChannel(Channel channel) throws Exception
                {
                    channel.pipeline().addLast("centerCommServerDecoder", new CenterCommServerDecoder());
                    channel.pipeline().addLast("centerCommServerPacketHandler", new CenterCommServerPacketHandler());
                }
            });
        }
        catch (Exception e) {
            this.log.error("UdpServerCenterComm.init: Exception: {}", e.toString());
        }

        log.info("===============================================================");
        log.info("=  UDP Center Communication Server Start.......................");
        log.info("=  bindAddress: {}", processConfig.getCenterBindAddr());
        log.info("=     bindPort: {}", processConfig.getCenterBindPort());
        log.info("===============================================================");

        try {
            if (this.processConfig.getCenterBindAddr().equals("0.0.0.0")) {
                this.bootstrap.bind(this.processConfig.getCenterBindPort());
            }
            else {
                this.bootstrap.bind(this.processConfig.getCenterBindAddr(), processConfig.getCenterBindPort());
            }
        }
        catch (Exception e) {
            this.log.error("UdpServerCenterComm.init: Bind Exception: {}", e.toString());
            this.nioEventLoopGroup.shutdownGracefully();
        }
        finally {
        }
        log.info("UdpServerCenterComm.init: ..End. {}", toString());
    }

}
