генерировать последовательный уникальный номер в диапазоне - PullRequest
0 голосов
/ 12 октября 2018

В моей базе данных есть поле для сохранения уникального номера с добавлением двух последних цифр года create_at.На данный момент все работает хорошо, за исключением того, что вместо использования метода SecureRandom я ищу вариант сохранения последовательных чисел.то есть.1901, 1902, 1903 ...

Модель

before_create :create_number

def create_number
    loop do
      self. number = ((created_at + 1.year).strftime("%y")).concat(sprintf '%02d', SecureRandom.random_number(200))
      break unless self.class.exists?(:number => number)
    end
  end

1 Ответ

0 голосов
/ 12 октября 2018

Ключ заключается в том, чтобы использовать запрос подсчета, чтобы получить количество записей для этого конкретного года:

class Thing < ApplicationRecord

  before_commit :create_number!, if: -> { number.nil? }

  private

  def count_records_from_same_year
    self.class.where(
      created_at: (created_at.beginning_of_year..created_at.end_of_year)
    ).count
  end

  def create_number!
    loop do
      year = (created_at + 1.year).strftime("%y")
      self.number = year.concat(sprintf '%02d', count_records_from_same_year)
      break unless self.class.where(number: self.number).exists?
    end
  end
end

Как вы можете видеть, он генерирует последовательные числа:

irb(main):001:0> Thing.create
   (0.3ms)  BEGIN
  Thing Create (1.3ms)  INSERT INTO "things" ("created_at", "updated_at") VALUES ($1, $2) RETURNING "id"  [["created_at", "2018-10-12 09:57:24.527527"], ["updated_at", "2018-10-12 09:57:24.527527"]]
   (1.2ms)  SELECT COUNT(*) FROM "things" WHERE "things"."created_at" BETWEEN $1 AND $2  [["created_at", "2018-01-01 00:00:00"], ["created_at", "2018-12-31 23:59:59.999999"]]
  Thing Exists (1.4ms)  SELECT  1 AS one FROM "things" WHERE "things"."number" = $1 LIMIT $2  [["number", "1901"], ["LIMIT", 1]]
   (0.7ms)  COMMIT
=> #<Thing id: 1, number: "1901", created_at: "2018-10-12 09:57:24", updated_at: "2018-10-12 09:57:24">
irb(main):002:0> Thing.create
   (0.3ms)  BEGIN
  Thing Create (0.8ms)  INSERT INTO "things" ("created_at", "updated_at") VALUES ($1, $2) RETURNING "id"  [["created_at", "2018-10-12 09:57:26.402797"], ["updated_at", "2018-10-12 09:57:26.402797"]]
   (0.7ms)  SELECT COUNT(*) FROM "things" WHERE "things"."created_at" BETWEEN $1 AND $2  [["created_at", "2018-01-01 00:00:00"], ["created_at", "2018-12-31 23:59:59.999999"]]
  Thing Exists (0.8ms)  SELECT  1 AS one FROM "things" WHERE "things"."number" = $1 LIMIT $2  [["number", "1902"], ["LIMIT", 1]]
   (0.7ms)  COMMIT
=> #<Thing id: 2, number: "1902", created_at: "2018-10-12 09:57:26", updated_at: "2018-10-12 09:57:26">
irb(main):003:0> Thing.create
   (0.5ms)  BEGIN
  Thing Create (0.7ms)  INSERT INTO "things" ("created_at", "updated_at") VALUES ($1, $2) RETURNING "id"  [["created_at", "2018-10-12 09:57:27.537635"], ["updated_at", "2018-10-12 09:57:27.537635"]]
   (1.6ms)  SELECT COUNT(*) FROM "things" WHERE "things"."created_at" BETWEEN $1 AND $2  [["created_at", "2018-01-01 00:00:00"], ["created_at", "2018-12-31 23:59:59.999999"]]
  Thing Exists (0.6ms)  SELECT  1 AS one FROM "things" WHERE "things"."number" = $1 LIMIT $2  [["number", "1903"], ["LIMIT", 1]]
   (0.7ms)  COMMIT
=> #<Thing id: 3, number: "1903", created_at: "2018-10-12 09:57:27", updated_at: "2018-10-12 09:57:27">
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...