func TestCustomTimestamp(t *testing.T) { // timestamp - epoch = adjusted time testCases := []struct { ts int64 adjTs int64 }{ {1397666977000, 72290977000}, // Now {1397666978000, 72290978000}, // in 1 second {1395881056000, 70505056000}, // 3 weeks ago {1303001162000, -22374838000}, // 3 years ago {1492390054000, 167014054000}, // in 3 years {2344466898000, 1019090898000}, // in 30 years } // Initialise our custom epoch epoch, err := time.Parse(time.RFC3339, defaultEpoch) require.NoError(t, err) epochMs := util.TimeToMsInt64(epoch) for _, tc := range testCases { adjTs := util.CustomTimestamp(epochMs, time.Unix(tc.ts/1000, 0)) assert.Equal(t, adjTs, tc.adjTs, "Times should match") } }
// Mint a new 64bit ID based on the current time, worker id and sequence func (sf *Snowflake) Mint() (string, error) { sf.Lock() defer sf.Unlock() // Setup locks in our configured options sf.once.Do(sf.setup) // Ensure we only mint IDs if correctly configured if sf.workerId > sf.maxWorkerId { return "", ErrInvalidWorkerId } // Get the current timestamp in ms, adjusted to our custom epoch t := util.CustomTimestamp(sf.epoch, time.Now()) // Update snowflake with this, which will increment sequence number if needed err := sf.update(t) if err != nil { return "", err } // Mint a new ID id := sf.mintId() return strconv.FormatUint(id, 10), nil }
func TestPreEpochTime(t *testing.T) { testCases := []time.Time{ time.Date(2012, 1, 0, 0, 0, 0, 0, time.UTC), time.Date(2011, 9, 5, 0, 0, 0, 0, time.UTC), time.Date(1066, 9, 5, 0, 0, 0, 0, time.UTC), } for _, tc := range testCases { sf, err := New(0) require.NoError(t, err) // Initialise our custom epoch epoch, err := time.Parse(time.RFC3339, defaultEpoch) require.NoError(t, err) epochMs := util.TimeToMsInt64(epoch) ts := util.CustomTimestamp(epochMs, tc) err = sf.update(ts) assert.Error(t, err) } }