Size: a a a

pro.rb (Ruby/Rails / RU)

2020 October 22

I

Igor in pro.rb (Ruby/Rails / RU)
Эрмек Каныбек уулу
используя какие инструменты для тестов - можно создать подобный случай принятия заказа многими водителями?
Тут бы логику описать бы

Например, заказ может иметь только одного водителя, и есть айдишник водителя проставляется в заказе, то, имхо, трабл быть не должно, либо лок записи решит возможную проблему
источник

I

Igor in pro.rb (Ruby/Rails / RU)
Эрмек Каныбек уулу
Заказ отправляется всем водителям одновременно.
Как именно присваивание заказа водителю происходит?
источник

ЭК

Эрмек Каныбек уулу... in pro.rb (Ruby/Rails / RU)
Igor
Как именно присваивание заказа водителю происходит?
  def accept
   order = Order.find(params[:order][:order_id])
   if order.nil?
     return render json: {success: false, data: "Ошибка: заказ не найден!"}
   end

   if order && order.status == OPEN
     unless @current_driver.balance_sufficient?(subtract_amount: order.tariff&.commission)
       return render json: {success: false, data: t("models.driver.errors.balance.insufficient", balance: @current_driver.balance, currency: CURRENCY)}, status: 200
     end

     if @current_driver.status == FREE
       if order.update_attributes(status: ACCEPTED, driver_id: @current_driver.id) && @current_driver.update_columns(status: ACCEPTED)
         order.save!
         render json: {success: true, tariff: Tariff.find(order.tariff_id)}, status: 200
       else
         order.save!
         render json: {success: false, data: 'Произошла ошибка'}, status: 200
       end
     else
       order.save!
       render json: {success: false, data: "Ваш статус должен быть свободен!"}, status: 200
     end
   else
     order.save!
     title = order.status == CANCELLED ? 'Заказ был отменен!' : 'Заказ уже занят!'
     render json: {success: false, data: title, order_status: order.status}, status: 200
   end
 end
источник

ЭК

Эрмек Каныбек уулу... in pro.rb (Ruby/Rails / RU)
lock здесь был убран. Redis тоже
источник

Т

Тенпеннай in pro.rb (Ruby/Rails / RU)
Эрмек Каныбек уулу
  def accept
   order = Order.find(params[:order][:order_id])
   if order.nil?
     return render json: {success: false, data: "Ошибка: заказ не найден!"}
   end

   if order && order.status == OPEN
     unless @current_driver.balance_sufficient?(subtract_amount: order.tariff&.commission)
       return render json: {success: false, data: t("models.driver.errors.balance.insufficient", balance: @current_driver.balance, currency: CURRENCY)}, status: 200
     end

     if @current_driver.status == FREE
       if order.update_attributes(status: ACCEPTED, driver_id: @current_driver.id) && @current_driver.update_columns(status: ACCEPTED)
         order.save!
         render json: {success: true, tariff: Tariff.find(order.tariff_id)}, status: 200
       else
         order.save!
         render json: {success: false, data: 'Произошла ошибка'}, status: 200
       end
     else
       order.save!
       render json: {success: false, data: "Ваш статус должен быть свободен!"}, status: 200
     end
   else
     order.save!
     title = order.status == CANCELLED ? 'Заказ был отменен!' : 'Заказ уже занят!'
     render json: {success: false, data: title, order_status: order.status}, status: 200
   end
 end
а зачем столько вызовов order.save! ?
источник

ЭК

Эрмек Каныбек уулу... in pro.rb (Ruby/Rails / RU)
видимо от lock осталось
источник

I

Igor in pro.rb (Ruby/Rails / RU)
Эрмек Каныбек уулу
  def accept
   order = Order.find(params[:order][:order_id])
   if order.nil?
     return render json: {success: false, data: "Ошибка: заказ не найден!"}
   end

   if order && order.status == OPEN
     unless @current_driver.balance_sufficient?(subtract_amount: order.tariff&.commission)
       return render json: {success: false, data: t("models.driver.errors.balance.insufficient", balance: @current_driver.balance, currency: CURRENCY)}, status: 200
     end

     if @current_driver.status == FREE
       if order.update_attributes(status: ACCEPTED, driver_id: @current_driver.id) && @current_driver.update_columns(status: ACCEPTED)
         order.save!
         render json: {success: true, tariff: Tariff.find(order.tariff_id)}, status: 200
       else
         order.save!
         render json: {success: false, data: 'Произошла ошибка'}, status: 200
       end
     else
       order.save!
       render json: {success: false, data: "Ваш статус должен быть свободен!"}, status: 200
     end
   else
     order.save!
     title = order.status == CANCELLED ? 'Заказ был отменен!' : 'Заказ уже занят!'
     render json: {success: false, data: title, order_status: order.status}, status: 200
   end
 end
Пишу с телефона
После проверки статуса ордена на free идёт нелогично обновление

Ты сначала обновлегься через update_attrobutes, а потом делаешь save!.

Попробуй, например, сделать присваивание атрибутов в заказ и водителю через assign_attributes, а в ифе сдедать
If order.save && current_driver.save
источник

I

Igor in pro.rb (Ruby/Rails / RU)
И добавь проверку на то, что водитель в заказе отсутствует
источник

I

Igor in pro.rb (Ruby/Rails / RU)
Return false if order.driver_id.present?
В начале такое
источник

AI

Alex Ilizarov in pro.rb (Ruby/Rails / RU)
Эрмек Каныбек уулу
используя какие инструменты для тестов - можно создать подобный случай принятия заказа многими водителями?
Race condition вообще плохо тестируется
источник

AI

Alex Ilizarov in pro.rb (Ruby/Rails / RU)
В целом плодишь несколько потоков и долбишь базу
источник

AI

Alex Ilizarov in pro.rb (Ruby/Rails / RU)
Потом логикой проверяешь что все все создано верно
источник

AI

Alex Ilizarov in pro.rb (Ruby/Rails / RU)
Но лучше конечно читать про уровни изоляции бд и идемпотентность запросов
источник

AI

Alex Ilizarov in pro.rb (Ruby/Rails / RU)
Эрмек Каныбек уулу
используя какие инструменты для тестов - можно создать подобный случай принятия заказа многими водителями?
Почитай обязательно статью яндекса на хабре как они в такси идемпотентность делали запросам. Иначе наступишь на кучу граблей.
источник

AI

Alex Ilizarov in pro.rb (Ruby/Rails / RU)
И не пиши сложную логику (в идеале вообще логику) в коде контроллера
источник

u

unkmas in pro.rb (Ruby/Rails / RU)
Слушайте, а в рельсе никак не сделать запрос UPDATE … SET.. WHERE.. RETURNING?

Всё облазил, даже в ареле не вижу как returning сделать. А exec_query как-то не очень красиво)
источник

ℹ🅿

ℹ️ 🅿️ in pro.rb (Ruby/Rails / RU)
unkmas
Слушайте, а в рельсе никак не сделать запрос UPDATE … SET.. WHERE.. RETURNING?

Всё облазил, даже в ареле не вижу как returning сделать. А exec_query как-то не очень красиво)
Вот не нашли тоже(
источник

RU

Roman Usherenko in pro.rb (Ruby/Rails / RU)
unkmas
Слушайте, а в рельсе никак не сделать запрос UPDATE … SET.. WHERE.. RETURNING?

Всё облазил, даже в ареле не вижу как returning сделать. А exec_query как-то не очень красиво)
есть подозрение, что это "не по рельсовски". а зачем тебе такое надо? логика на хранимых процедурах?
источник

u

unkmas in pro.rb (Ruby/Rails / RU)
Не, хранимки не при чём) Просто сделать update_all и получить список изменённых записей, а не просто количество
источник

ch

central hardware in pro.rb (Ruby/Rails / RU)
Эрмек Каныбек уулу
  def accept
   order = Order.find(params[:order][:order_id])
   if order.nil?
     return render json: {success: false, data: "Ошибка: заказ не найден!"}
   end

   if order && order.status == OPEN
     unless @current_driver.balance_sufficient?(subtract_amount: order.tariff&.commission)
       return render json: {success: false, data: t("models.driver.errors.balance.insufficient", balance: @current_driver.balance, currency: CURRENCY)}, status: 200
     end

     if @current_driver.status == FREE
       if order.update_attributes(status: ACCEPTED, driver_id: @current_driver.id) && @current_driver.update_columns(status: ACCEPTED)
         order.save!
         render json: {success: true, tariff: Tariff.find(order.tariff_id)}, status: 200
       else
         order.save!
         render json: {success: false, data: 'Произошла ошибка'}, status: 200
       end
     else
       order.save!
       render json: {success: false, data: "Ваш статус должен быть свободен!"}, status: 200
     end
   else
     order.save!
     title = order.status == CANCELLED ? 'Заказ был отменен!' : 'Заказ уже занят!'
     render json: {success: false, data: title, order_status: order.status}, status: 200
   end
 end
Offtop а вас в этом коде не смущает обилие вложенных условий?
источник