LINUX.ORG.RU

игровая валюта, покупки в игре и т.п.

 , ,


0

1

это не тред с конкретным вопросом, скорее тред размышлений. захотелось на досуге накактать некую браузерку, технологии не пренципиальны но перечислинны в тегах. встал вопрос покупок в игре. как это правильно делать? в реляционках, наверное, это можно оборачивать транзакцией. пока пробую провернуть покупку через find_and_modify или update, но как-то кажется есть более правильный вариант.

тоесть.

например есть игрок, у него есть баланс. он может купупить предмет. это все просто. но если условие более сложное, например, если игрок может нанять бойца но только если есть куда его поселить (построена казарма). витоге все это выростает в запрос который я даже не могу сформулировать, так как все это знаю на уровне «от№@сь». накидайте каких-то ссылок полезных для размышлений, давно таким не страдал, вот, собственно.

★★★

Последнее исправление: cetjs2 (всего исправлений: 1)

как-то сумбурно вышло.

вот есть у игрока баланс, он хочет что-то купить, если единственное условие покупки — наличие денег, то тут все просто, я делаю find_and_modify, с условиями balance $gte price и если получаю объект — покупка прошла, но если условия более сложные как быть

trashymichael ★★★
() автор топика
Ответ на: комментарий от zz

ну редис это я так приписал, я его пока лишь для сессий использую и то, не использую а планирую

trashymichael ★★★
() автор топика
Ответ на: комментарий от zz

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

trashymichael ★★★
() автор топика

по ходу возник такой вопрос, насколько смертельно делать из хендлера торнадо неасинхронный вызов, ну тоесть вместо asyncmongо, скажем, использовать обычный pymongo? что случится с торнадо если такой вызов зависнет?

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

ибо asyncmongo какой-то кастрированный и не всегда подходит, как я понимаю и монга и редис очень быстро работают на селект особенно, и преступлением не будет парочка синхронных вызовов, возможно даже наоборот перебор асинхронности негативно скажется, особенно проблематично все это в реализации сессий например, когда нужны вызовы не из самих get/post/put/etc методов, возможно я не доконца понимаю идею, gen.engine вроде как уже устарел а coroutine должен возвращать промис, тоесть если мне не в хендлере но в фукнционале который хендлер использует нужен асинхронный вызов, что мне делать, забить и делать синхронный или как изголяться ?

trashymichael ★★★
() автор топика

на счет покупок, возможно есть резон сделать это через pubsub и очередь, тоесть завести отдельный поток который синхронно все это обрабатывает поочередно, это исключит накладки и т.п. наверное надо пробовать, подожду кто что скажет вобщем...

trashymichael ★★★
() автор топика
Ответ на: комментарий от risenshnobel

действительно жутко и неясно выглядит, хочется простоты и элегантности

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

покачто отдельный сервер обработки покупок мне кажется самым приемлемым но и самым геморным вариантом

trashymichael ★★★
() автор топика

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

В идеале КАЖДЫЙ предмет должен иметь уникальный ID и лог операций, с ним связанных — кто купил, кому продал/подобрал/выбросил. Если это пачка предметов — то при разделении пачки у той части, которую игрок отделил, должна появиться в логе запись, из какой пачки она вынута, а у оригинальнй пачки — сколько из неё изъято. При объединении стеков, соответственно, наоборот. Поможет в случае багов и для предотвращения их использования читерами — например, если из пачки в 100 предметов вынуто 60, то в ней должно остаться 40, если же осталось другое число, то в твоей системе баг и кто-то пытается с его помощью дюпать предметы.

INFOMAN ★★★★★
()
Последнее исправление: INFOMAN (всего исправлений: 1)
Ответ на: комментарий от trashymichael

Ну я так понял ты рассматриваешь возможность переноса...

Suntechnic ★★★★★
()
Ответ на: комментарий от Suntechnic

Как выносить перед транзакцией любые проверки? Это же просто автоматически дает двойные-тройные покупки.

zz ★★★★
()
Ответ на: комментарий от INFOMAN

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

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

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

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

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

p.s. кстати, я бы послушал как кто делал/делает и на других технологиях, это не принципиально же

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

короче пока я решил пока сделать отдельный маленький внутренний серверок который и будет все оплаты-покупки производить поочереди, а из торнадо с ним связь держать через http async client, что скажете?

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

думалось сначала это как-то через редис-медиатор сделать в отдельом потоке,но ведь инстансов может быть много

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

Я реализовал покупку тем же способом, что и все остальные действия юзера. У меня рантайм, и по сути все запросы в бд я делаю опоследованно*.

*Нет такого слова, но мне его явно не хватает, оно означает в произвольный момент после :)

special-k ★★★★
()
Последнее исправление: special-k (всего исправлений: 1)
Ответ на: комментарий от special-k

что значит «рантайм» и «опоследовательно» в данном контексте. ты хочешь сказать что пока один хендлер работает остальные ждут или как?

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

проблема тут не в том чтоб в бд уменьшить/увеличить баланс, а чтоб произвести проверки и прочие манипуляции, куда-то что-то добавить, удалить, и т.п.

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

Ну рантайм.. игровой сервер забирает данные и держит их в памяти (пока работает), не только покупка в игре связана с условиями, все операции пользователя связаны с условиями - это часть игровой логики. И не каждое обращение к серверу связано с обращением к бд (их слишком много.. у меня реалтайм).

special-k ★★★★
()
Последнее исправление: special-k (всего исправлений: 2)
Ответ на: комментарий от trashymichael

В общем, я бы делал единый механизм для проведения всех игровых операций, от каста заклинаний, до покупки лошади, а обеспечение проведения транзакций решал бы опоследованно) в рамках отдельной задачи. Выносить какие-то операции за пределы игровой логики слишком сложно (для меня по крайней мере).

Что касается непосредственно реализации, то у меня для каждой операции вызывается проверочный метод, например так

def some_condition new_value
  thing_kind = new_value[KIND_KEY]
  store = world.stores[ new_value[STORE_ID_KEY] ]
  raise ConditionError if store.nil?
  raise ConditionError unless store.buyable_thing? thing_kind, user
  { kind: thing_kind, store: store }
end
Вот такой метод, на самом деле, он может быть несколько сложнее, но суть в том, что он проверяет валидность параметров в соответствии с игровой логикой, если параметры не соответствуют, он возвращает ошибку, иначе возвращает данные в нужной форме. Мне удобно выстраивать условия вертикально, так их может быть сколь угодно много и они останутся хорошо читаемыми. К тому же можно делать ветвления типа
if a == 1
  raise ConditionError if some_condition1?
else
  raise ConditionError if some_condition2?
end
Короче, у меня прижился данный «паттерн».

special-k ★★★★
()
Ответ на: комментарий от special-k

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

trashymichael ★★★
() автор топика
Ответ на: комментарий от trashymichael

Уточняю, ты спросил, как обеспечить проверку условий при покупке, я ответил, что так же, как и при любом другом действии. Сохранность транзакций - это уже другая задача.

будет ли оно так эффективней

Очевидно. Сколько нужно времени, чтобы сохранить информацию в массив, и сколько нужно времени, чтобы сохранить информацию в БД, разница во много порядков.. Общение через БД несет огромный оверхед..

что делать когда несколько инстансов сервера?

Эту проблему еще никто не решил, так что вряд ли я дам тебе односложный ответ) К тому же юзер всеравно привязан к серверу сокетом..

Кстати можешь зайти по ссылке в профиле (если интересно), я как раз обучение добавил..

special-k ★★★★
()

встал вопрос покупок в игре. как это правильно делать?

Лучше девку найди, живую, и сделай её правильно.

«Нанять бойца», мля, виртуального. Смешная молодёжь пошла.

yvv ★★☆
()
Ответ на: комментарий от yvv

окей, представь что это азартная игра или что-либо другое, более «взрослое». и вообще я семейный человек, ахах, по-ходу ты тут единственный лох без «девки», судя по количеству яда твоего поста

trashymichael ★★★
() автор топика
Ответ на: комментарий от special-k

ну смотри, если это бд то я ставлю ее на крутой сервер в 1 инстанс и запускаю несколько инстансов фронта (ну всмысле бека, хттп сервера), либо делаю реплики-шардинги, что там оно как, в рантайме это все уже надо руками разруливать и витоге одно на одно выходит. я пока всеж пробую провернуть вариант с апдейтом, и уж если он не проканал выясняю причины чего не хватило.

trashymichael ★★★
() автор топика
Ответ на: комментарий от special-k

посмотрел, у тебя действительно зело рилтайм потому рантайм тут будет единоверным решением, у меня все более оффлайновое

trashymichael ★★★
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.