人人網框架導入uidGenerator的ID生成方式


人人網框架導入uidGenerator的ID生成方式

2019-03-11
LIUREN
 

人人網框架導入uidGenerator的ID生成方式

人人網框架導入uidGenerator的ID生成方式

安裝環境

開發工具:Eclipse
Maven版本:apache-maven-3.5.2
java jdk 1.8
MySQL版本:5.7

一.在renren-api

創建一個節點表worker_node,創建語句:

CREATE TABLE `worker_node` (
  `ID` bigint(20) NOT NULL AUTO_INCREMENT COMMENT 'auto increment id',
  `HOST_NAME` varchar(64) NOT NULL COMMENT 'host name',
  `PORT` varchar(64) NOT NULL COMMENT 'port',
  `TYPE` int(11) NOT NULL COMMENT 'node type: ACTUAL or CONTAINER',
  `LAUNCH_DATE` date NOT NULL COMMENT 'launch date',
  `MODIFIED` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT 'modified time',
  `CREATED` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00' COMMENT 'created time',
  PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=10 DEFAULT CHARSET=utf8 COMMENT='DB WorkerID Assigner for UID Generator';

二.在renren-security項目中的pom.xml中添加相應的架包

pom.xml添加架包內容如下:

<!--必須放在最后--> <dependency> <groupId>cn.codesheep</groupId> <artifactId>uid-generator</artifactId> <version>1.0</version> </dependency> 

三.在renren-apiio.renren.config的文件中增加文件

CachedUidGeneratorConfig

/** * @author lr * @date 2019年3月8日 下午4:03:15 * @version V1.0.0 */ package io.renren.config; import com.baidu.fsg.uid.impl.CachedUidGenerator; import io.renren.service.DisposableWorkerIdAssigner; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; /** * https://github.com/baidu/uid-generator/blob/master/README.zh_cn.md * 百度id生成器 * 兩種生成器: DefaultUidGenerator、CachedUidGenerator。如對UID生成性能有要求, 請使用CachedUidGenerator * 對應Spring配置分別為: default-uid-spring.xml、cached-uid-spring.xml */ @Configuration public class CachedUidGeneratorConfig { /** * 用完即棄的WorkerIdAssigner, 依賴DB操作 * @return */ @Bean public DisposableWorkerIdAssigner disposableWorkerIdAssigner(){ return new DisposableWorkerIdAssigner(); } @Bean public CachedUidGenerator cachedUidGenerator(DisposableWorkerIdAssigner disposableWorkerIdAssigner){ CachedUidGenerator cachedUidGenerator = new CachedUidGenerator(); cachedUidGenerator.setWorkerIdAssigner(disposableWorkerIdAssigner); //以下為可選配置, 如未指定將采用默認值 cachedUidGenerator.setTimeBits(29); cachedUidGenerator.setWorkerBits(21); cachedUidGenerator.setSeqBits(13); cachedUidGenerator.setEpochStr("2016-09-20"); //RingBuffer size擴容參數, 可提高UID生成的吞吐量 //默認:3, 原bufferSize=8192, 擴容后bufferSize= 8192 << 3 = 65536 cachedUidGenerator.setBoostPower(3); // 指定何時向RingBuffer中填充UID, 取值為百分比(0, 100), 默認為50 // 舉例: bufferSize=1024, paddingFactor=50 -> threshold=1024 * 50 / 100 = 512. // 當環上可用UID數量 < 512時, 將自動對RingBuffer進行填充補全 //<property name="paddingFactor" value="50"></property> //另外一種RingBuffer填充時機, 在Schedule線程中, 周期性檢查填充 //默認:不配置此項, 即不實用Schedule線程. 如需使用, 請指定Schedule線程時間間隔, 單位:秒 cachedUidGenerator.setScheduleInterval(60L); //拒絕策略: 當環已滿, 無法繼續填充時 //默認無需指定, 將丟棄Put操作, 僅日志記錄. 如有特殊需求, 請實現RejectedPutBufferHandler接口(支持Lambda表達式) //<property name="rejectedPutBufferHandler" ref="XxxxYourPutRejectPolicy"></property> //cachedUidGenerator.setRejectedPutBufferHandler(); //拒絕策略: 當環已空, 無法繼續獲取時 --> //默認無需指定, 將記錄日志, 並拋出UidGenerateException異常. 如有特殊需求, 請實現RejectedTakeBufferHandler接口(支持Lambda表達式) --> //<property name="rejectedTakeBufferHandler" ref="XxxxYourTakeRejectPolicy"></property> return cachedUidGenerator; } } 

四.在renren-apiio.renren.dao的文件中增加文件

WorkerNodeDao.java

/* * Copyright (c) 2017 Baidu, Inc. All Rights Reserve. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package io.renren.dao; import org.apache.ibatis.annotations.Mapper; import org.apache.ibatis.annotations.Param; import com.baidu.fsg.uid.worker.entity.WorkerNodeEntity; /** * DAO for M_WORKER_NODE * * @author yutianbao */ @Mapper public interface WorkerNodeDao { /** * Get {@link WorkerNodeEntity} by node host * * @param host * @param port * @return */ WorkerNodeEntity getWorkerNodeByHostPort(@Param("host") String host, @Param("port") String port); /** * Add {@link WorkerNodeEntity} * * @param workerNodeEntity */ void addWorkerNode(WorkerNodeEntity workerNodeEntity); } 

五.在renren-apiio.renren.service的文件中增加文件

/* * Copyright (c) 2017 Baidu, Inc. All Rights Reserve. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package io.renren.service; import javax.annotation.Resource; import org.apache.commons.lang.math.RandomUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.transaction.annotation.Transactional; import com.baidu.fsg.uid.utils.DockerUtils; import com.baidu.fsg.uid.utils.NetUtils; import com.baidu.fsg.uid.worker.WorkerIdAssigner; import com.baidu.fsg.uid.worker.WorkerNodeType; import com.baidu.fsg.uid.worker.entity.WorkerNodeEntity; import io.renren.dao.WorkerNodeDao; /** * Represents an implementation of {@link WorkerIdAssigner}, * the worker id will be discarded after assigned to the UidGenerator * * @author yutianbao */ public class DisposableWorkerIdAssigner implements WorkerIdAssigner { private static final Logger LOGGER = LoggerFactory.getLogger(DisposableWorkerIdAssigner.class); @Resource private WorkerNodeDao workerNodeDao; /** * Assign worker id base on database.<p> * If there is host name & port in the environment, we considered that the node runs in Docker container<br> * Otherwise, the node runs on an actual machine. * * @return assigned worker id */ @Transactional public long assignWorkerId() { // build worker node entity WorkerNodeEntity workerNodeEntity = buildWorkerNode(); // add worker node for new (ignore the same IP + PORT) workerNodeDao.addWorkerNode(workerNodeEntity); LOGGER.info("Add worker node:" + workerNodeEntity); return workerNodeEntity.getId(); } /** * Build worker node entity by IP and PORT */ private WorkerNodeEntity buildWorkerNode() { WorkerNodeEntity workerNodeEntity = new WorkerNodeEntity(); if (DockerUtils.isDocker()) { workerNodeEntity.setType(WorkerNodeType.CONTAINER.value()); workerNodeEntity.setHostName(DockerUtils.getDockerHost()); workerNodeEntity.setPort(DockerUtils.getDockerPort()); } else { workerNodeEntity.setType(WorkerNodeType.ACTUAL.value()); workerNodeEntity.setHostName(NetUtils.getLocalAddress()); workerNodeEntity.setPort(System.currentTimeMillis() + "-" + RandomUtils.nextInt(100000)); } return workerNodeEntity; } } 

六.在renren-apisrc/main/resources/mapper/的文件中增加文件WorkerNodeDao.xml

WorkerNodeDao.xml

<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="io.renren.dao.WorkerNodeDao"> <resultMap id="workerNodeRes" type="com.baidu.fsg.uid.worker.entity.WorkerNodeEntity"> <id column="ID" jdbcType="BIGINT" property="id" /> <result column="HOST_NAME" jdbcType="VARCHAR" property="hostName" /> <result column="PORT" jdbcType="VARCHAR" property="port" /> <result column="TYPE" jdbcType="INTEGER" property="type" /> <result column="LAUNCH_DATE" jdbcType="DATE" property="launchDate" /> <result column="MODIFIED" jdbcType="TIMESTAMP" property="modified" /> <result column="CREATED" jdbcType="TIMESTAMP" property="created" /> </resultMap> <insert id="addWorkerNode" useGeneratedKeys="true" keyProperty="id" parameterType="com.baidu.fsg.uid.worker.entity.WorkerNodeEntity"> INSERT INTO WORKER_NODE (HOST_NAME, PORT, TYPE, LAUNCH_DATE, MODIFIED, CREATED) VALUES ( #{hostName}, #{port}, #{type}, #{launchDate}, NOW(), NOW()) </insert> <select id="getWorkerNodeByHostPort" resultMap="workerNodeRes"> SELECT ID, HOST_NAME, PORT, TYPE, LAUNCH_DATE, MODIFIED, CREATED FROM WORKER_NODE WHERE HOST_NAME = #{host} AND PORT = #{port} </select> </mapper> 

七.在renren-api的Controller中編寫生成方法

ApiTestController.java

/** * Copyright (c) 2016-2019 人人開源 All rights reserved. * * https://www.renren.io * * 版權所有,侵權必究! */ package io.renren.controller; import io.renren.annotation.Login; import io.renren.annotation.LoginUser; import io.renren.common.utils.R; import io.renren.entity.UserEntity; import io.swagger.annotations.Api; import io.swagger.annotations.ApiOperation; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RequestAttribute; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import com.baidu.fsg.uid.UidGenerator; import springfox.documentation.annotations.ApiIgnore; /** * 測試接口 * * @author Mark sunlightcs@gmail.com */ @RestController @RequestMapping("/api") @Api(tags="測試接口") public class ApiTestController { @Autowired private UidGenerator uidGenerator; @Login @GetMapping("userInfo") @ApiOperation(value="獲取用戶信息", response=UserEntity.class) public R userInfo(@ApiIgnore @LoginUser UserEntity user){ return R.ok().put("user", user); } @Login @GetMapping("userId") @ApiOperation("獲取用戶ID") public R userInfo(@ApiIgnore @RequestAttribute("userId") Integer userId){ return R.ok().put("userId", userId); } @GetMapping("notToken") @ApiOperation("忽略Token驗證測試") public R notToken(){ return R.ok().put("msg", "無需token也能訪問。。。"); } @GetMapping("uuid") @ApiOperation("百度生成uid") public R uidGenerator(){ return R.ok().put("uid", Long.toString(uidGenerator.getUID())); } } 

七.在renren-api中執行ApiApplication.java

項目運行后訪問地址:http://localhost:8081/renren-api/api/uuid

訪問結果:

{"msg":"success","uid":"1340011929288130560","code":0}

=======================================================================================

博客地址:https://www.codepeople.cn

=======================================================================================

微信公眾號:

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM