.NET 分布式自增Id組件(解決自動分配機器Id、時間回撥問題)


目錄

簡介

IdHelper是一個.NET(支持.NET45+或.NET Standard2+)生成分布式趨勢自增Id組件,有兩個版本:原始版為基於雪花Id(不了解請自行百度)方案,需要手動管理設置WorkerId;完美版在原始版的基礎上使用Zookeeper來解決原始版中的WorkerId的分配問題和時間回撥問題。

原始版安裝方式:Nuget安裝IdHelper即可

完美版安裝方式:Nuget安裝IdHelper.Zookeeper即可

請按需選擇,強烈推薦完美版

項目地址:https://github.com/Coldairarrow/IdHelper

產生背景

分布式趨勢自增Id的生成方案比較多,其中雪花Id是比較常用的,但是雪花Id及其依賴WorkerId的分配和機器時鍾。WorkerId分配問題:傳統雪花Id是需要分配數據中心Id和機器Id(即WorkerId),我為了使用方便(項目比較小),用不到數據中心Id,就把數據中心Id去掉並補充到機器Id,使機器Id可分配范圍為1~1023,每個服務機器Id不能重復,若手工去為每個服務設置無疑十分麻煩還容易搞錯(其實是)。時鍾回撥問題:由於強依賴機器時鍾,因此當時間回撥時將發生災難性問題,雖然這種概率很小,但是實際存在。為了解決上述兩個問題,本組件應運而生。

使用方式

原始版

Nuget安裝包:IdHelper

剛出爐的包,排名比較靠后,請認准作者:Coldairarrow

using Coldairarrow.Util;
using System;

namespace Demo
{
    class Program
    {
        static void Main(string[] args)
        {
            new IdHelperBootstrapper()
                //設置WorkerId
                .SetWorkderId(1)
                .Boot();

            Console.WriteLine($"WorkerId:{IdHelper.WorkerId},Id:{IdHelper.GetId()}");

            Console.ReadLine();
        }
    }
}

完美版

1:安裝並配置JAVA環境(Zookeeper需要用JAVA) 教程:連接

2:安裝並啟動Zookeeper,教程:鏈接

3:Nuget安裝包:IdHelper.Zookeeper

using Coldairarrow.Util;
using System;

namespace Demo.Zookeeper
{
    class Program
    {
        static void Main(string[] args)
        {
            new IdHelperBootstrapper()
                //使用Zookeeper自動分配管理WorkerId,解決時間回退問題和自動分配問題
                .UseZookeeper("127.0.0.1:2181", 200, "Test")
                .Boot();

            Console.WriteLine($"WorkerId:{IdHelper.WorkerId},Id:{IdHelper.GetId()}");

            Console.ReadLine();
        }
    }
}

測試

using Coldairarrow.Util;
using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Threading.Tasks;

namespace Demo.Test
{
    class Program
    {
        static void Main(string[] args)
        {
            string conString = "127.0.0.1:2181";
            new IdHelperBootstrapper()
                .UseZookeeper(conString, 200, "Test")
                .Boot();

            Console.WriteLine($"WorkerId:{IdHelper.WorkerId}");

            Stopwatch watch = new Stopwatch();
            watch.Start();
            List<Task> tasks = new List<Task>();
            BlockingCollection<string> ids = new BlockingCollection<string>();
            for (int i = 0; i < 4; i++)
            {
                tasks.Add(Task.Run(() =>
                {
                    for (int j = 0; j < 1000000; j++)
                    {
                        ids.Add(IdHelper.GetId());
                    }
                }));
            }
            Task.WaitAll(tasks.ToArray());
            watch.Stop();
            Console.WriteLine($"耗時:{watch.ElapsedMilliseconds}ms,是否有重復:{ids.Count != ids.Distinct().Count()}");
        }
    }
}

結尾

以上所有示例在源碼中都有,若覺得不錯請點贊加星星,希望能夠幫助到大家。

有任何問題請及時反饋或加群交流

QQ群1:(已滿)

QQ群2:579202910


免責聲明!

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



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