-
Notifications
You must be signed in to change notification settings - Fork 0
ED-305: withdrawal repair tools #411
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from 11 commits
5b5e9f5
79ba4ac
0c840f8
9ce0cc8
2ac5866
d4d2560
3453354
3e038fd
81dd416
9cd2b17
29c5b9e
925fc00
0a215a6
2c61ba2
d110a7f
88e353f
3fcf80a
0bd5760
40d3cf6
97ee16f
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,4 +1,4 @@ | ||
| -module(ff_withdrawal_repair). | ||
| -module(ff_withdrawal_repair_handler). | ||
|
|
||
| -behaviour(ff_woody_wrapper). | ||
|
|
||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -7,6 +7,8 @@ | |
| -include_lib("damsel/include/dmsl_payment_processing_thrift.hrl"). | ||
| -include_lib("damsel/include/dmsl_withdrawals_provider_adapter_thrift.hrl"). | ||
|
|
||
| -include_lib("fistful_proto/include/ff_proto_withdrawal_thrift.hrl"). | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. А зачем тут новый include? Чё-то не вижу сходу потребности.(как кстати и в предыдущем include) |
||
|
|
||
| -type id() :: binary(). | ||
| -type clock() :: ff_transaction:clock(). | ||
|
|
||
|
|
@@ -24,6 +26,7 @@ | |
| attempts => attempts(), | ||
| resource => destination_resource(), | ||
| adjustments => adjustments_index(), | ||
| repair_scenario => repair_scenario(), | ||
| status => status(), | ||
| metadata => metadata(), | ||
| external_id => id() | ||
|
|
@@ -170,7 +173,7 @@ | |
| -type invalid_withdrawal_status_error() :: | ||
| {invalid_withdrawal_status, status()}. | ||
|
|
||
| -type action() :: sleep | continue | undefined. | ||
| -type action() :: sleep | continue | undefined | {set_timer, integer()}. | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Тогда это изменение тоже можно убрать. |
||
|
|
||
| -export_type([withdrawal/0]). | ||
| -export_type([withdrawal_state/0]). | ||
|
|
@@ -204,6 +207,7 @@ | |
| -export([id/1]). | ||
| -export([body/1]). | ||
| -export([status/1]). | ||
| -export([activity/1]). | ||
| -export([route/1]). | ||
| -export([attempts/1]). | ||
| -export([external_id/1]). | ||
|
|
@@ -223,6 +227,7 @@ | |
| -export([start_adjustment/2]). | ||
| -export([find_adjustment/2]). | ||
| -export([adjustments/1]). | ||
| -export([start_repair/2]). | ||
| -export([effective_final_cash_flow/1]). | ||
| -export([sessions/1]). | ||
| -export([session_id/1]). | ||
|
|
@@ -260,6 +265,7 @@ | |
| -type adjustment() :: ff_adjustment:adjustment(). | ||
| -type adjustment_id() :: ff_adjustment:id(). | ||
| -type adjustments_index() :: ff_adjustment_utils:index(). | ||
| -type repair_scenario() :: ff_repair:scenario(). | ||
| -type currency_id() :: ff_currency:id(). | ||
| -type party_revision() :: ff_party:revision(). | ||
| -type domain_revision() :: ff_domain_config:revision(). | ||
|
|
@@ -307,7 +313,7 @@ | |
|
|
||
| -type fail_type() :: | ||
| limit_check | ||
| | route_not_found | ||
| | route_not_found | {route_not_found, binary()} | ||
| | {inconsistent_quote_route, {provider_id, provider_id()} | {terminal_id, terminal_id()}} | ||
| | session. | ||
|
|
||
|
|
@@ -355,6 +361,10 @@ status(T) -> | |
| route(T) -> | ||
| maps:get(route, T, undefined). | ||
|
|
||
| -spec activity(withdrawal_state()) -> activity(). | ||
| activity(T) -> | ||
| deduce_activity(T). | ||
|
|
||
| -spec attempts(withdrawal_state()) -> attempts(). | ||
| attempts(#{attempts := Attempts}) -> | ||
| Attempts; | ||
|
|
@@ -446,7 +456,7 @@ create(Params) -> | |
| destination_id => DestinationID, | ||
| quote => Quote | ||
| }), | ||
| [ | ||
| Result = [ | ||
| {created, | ||
| genlib_map:compact(#{ | ||
| version => ?ACTUAL_FORMAT_VERSION, | ||
|
|
@@ -462,7 +472,8 @@ create(Params) -> | |
| })}, | ||
| {status_changed, pending}, | ||
| {resource_got, Resource} | ||
| ] | ||
| ], | ||
| Result | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Какое-то немного бессмысленное изменение, не?
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Плохо почистил всё после того как вставлял printf'ы, еще приберусь. |
||
| end). | ||
|
|
||
| create_resource( | ||
|
|
@@ -537,12 +548,31 @@ is_finished(#{status := {failed, _}}) -> | |
| is_finished(#{status := pending}) -> | ||
| false. | ||
|
|
||
| -spec start_repair(repair_scenario(), withdrawal_state()) -> {ok, process_result()}. | ||
| start_repair(Scenario, St) -> | ||
| Activity = ff_withdrawal:activity(St), | ||
| %TODO: после вызова process_transfer активити заново высчитывается, надо продумать правильно ли здесь проверять совместимость со сценарием | ||
| ok = check_activity_compatibility(Scenario, Activity), | ||
| RepairState = St#{repair_scenario => Scenario}, | ||
| {ok, process_transfer(RepairState)}. | ||
|
|
||
| check_activity_compatibility({routing, _}, Activity) when Activity =:= routing -> | ||
| ok; | ||
| %TODO: activity_not_compatible_with_scenario - или что-то другое? Реализовать в протоколе и тут | ||
| check_activity_compatibility(Scenario, Activity) -> | ||
| throw({exception, {activity_not_compatible_with_scenario, Activity, Scenario}}). | ||
|
|
||
| %% Transfer callbacks | ||
|
|
||
| -spec process_transfer(withdrawal_state()) -> process_result(). | ||
| process_transfer(Withdrawal) -> | ||
| Activity = deduce_activity(Withdrawal), | ||
| do_process_transfer(Activity, Withdrawal). | ||
| case Withdrawal of | ||
| #{repair_scenario := RepairScenario} -> | ||
| do_process_repair(RepairScenario, Withdrawal); | ||
| _ -> | ||
| do_process_transfer(Activity, Withdrawal) | ||
| end. | ||
|
|
||
| %% | ||
|
|
||
|
|
@@ -729,6 +759,10 @@ do_finished_activity(#{status := succeeded, p_transfer := committed}) -> | |
| do_finished_activity(#{status := {failed, _}, p_transfer := cancelled}) -> | ||
| stop. | ||
|
|
||
| -spec do_process_repair(repair_scenario(), withdrawal_state()) -> process_result(). | ||
| do_process_repair(Scenario, Withdrawal) -> | ||
| process_repair(Scenario, Withdrawal). | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Нахожу эту функцию немного бессмысленной. 🤔 Зачем она тут?
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Это небольшой артефакт, который остался после того как я пробовал разные варианты запуска сценария починки. Сначала я эту функцию завел для единообразия с do_process_transfer, а потом оказалось что здесь делать нечего, но пока я это оставил. Выпилю, если она пустой останется. |
||
|
|
||
| -spec do_process_transfer(activity(), withdrawal_state()) -> process_result(). | ||
| do_process_transfer(routing, Withdrawal) -> | ||
| process_routing(Withdrawal); | ||
|
|
@@ -761,6 +795,12 @@ do_process_transfer(adjustment, Withdrawal) -> | |
| do_process_transfer(stop, _Withdrawal) -> | ||
| {undefined, []}. | ||
|
|
||
| -spec process_repair(repair_scenario(), withdrawal_state()) -> process_result(). | ||
| process_repair({routing, {route_changed, Route}}, _Withdrawal) -> | ||
| {{set_timer, 0}, [{route_changed, Route}]}; | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. А зачем новый action? Чем это от
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
| process_repair({routing, {route_not_found, _} = FailType}, Withdrawal) -> | ||
| process_transfer_fail(FailType, Withdrawal). | ||
|
|
||
| -spec process_routing(withdrawal_state()) -> process_result(). | ||
| process_routing(Withdrawal) -> | ||
| case do_process_routing(Withdrawal) of | ||
|
|
@@ -1350,6 +1390,7 @@ get_current_session_status(Withdrawal) -> | |
| pending | ||
| end. | ||
|
|
||
|
|
||
| %% Withdrawal validators | ||
|
|
||
| -spec validate_withdrawal_creation(terms(), body(), wallet(), destination()) -> | ||
|
|
@@ -1726,9 +1767,11 @@ build_failure(limit_check, Withdrawal) -> | |
| } | ||
| end; | ||
| build_failure(route_not_found, _Withdrawal) -> | ||
| #{ | ||
| code => <<"no_route_found">> | ||
| }; | ||
| #{code => <<"no_route_found">>}; | ||
| build_failure({route_not_found, undefined}, Withdrawal) -> | ||
| build_failure(route_not_found, Withdrawal); | ||
| build_failure({route_not_found, Reason}, _Withdrawal) -> | ||
| #{code => Reason}; | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Вообще выглядит немного странно: сценарий называется
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Задумка была в том, что тот кто запустит восстановление по сценарию route_not_found напишет Reason, и это можно будет легко найти в логах, либо спустя время вспомнить что это был не просто "no_route_found", а что-то типа "Hand repair with no_route_found". Я упустил, что в этом случае в Reason'е может не оказаться слов про no_route_found (по умолчанию если инициатор поленится указать Reason, то будет дефолтное Тут два варианта, либо вообще Reason выпилить, либо вместо
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. (подозреваю, что поле 'code' задумывалось как нехудожественное короткое обозначение ошибки, и значит не надо там писать никаких ризонов, короче наверное надо просто выпилить Reason и всё)
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Я думаю, что для такого сценарий должен по-другому называться, типа
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Для текущего сценария определённо. |
||
| build_failure({inconsistent_quote_route, {Type, FoundID}}, Withdrawal) -> | ||
| Details = | ||
| {inconsistent_quote_route, #{ | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -188,8 +188,18 @@ process_call(CallArgs, _Machine, _, _Opts) -> | |
|
|
||
| -spec process_repair(ff_repair:scenario(), machine(), handler_args(), handler_opts()) -> | ||
| {ok, {repair_response(), result()}} | {error, repair_error()}. | ||
| process_repair({add_events, _} = Scenario, Machine, _Args, _Opts) -> | ||
| ff_repair:apply_scenario(ff_withdrawal, Machine, Scenario); | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Кажется по задумке автора |
||
| process_repair(Scenario, Machine, _Args, _Opts) -> | ||
| ff_repair:apply_scenario(ff_withdrawal, Machine, Scenario). | ||
| St = ff_machine:collapse(ff_withdrawal, Machine), | ||
| {ok, ScenarioResult} = ff_withdrawal:start_repair(Scenario, withdrawal(St)), | ||
| ProcessedResult = process_result(ScenarioResult, St), | ||
| case ff_repair:validate_scenario_result(ff_withdrawal, Machine, ProcessedResult) of | ||
| {ok, valid} -> | ||
| {ok, {ok, ProcessedResult}}; | ||
| {error, _Reason} = Error -> | ||
| {Error, #{}} | ||
| end. | ||
|
|
||
| -spec do_start_adjustment(adjustment_params(), machine()) -> {Response, result()} when | ||
| Response :: ok | {error, ff_withdrawal:start_adjustment_error()}. | ||
|
|
@@ -229,7 +239,9 @@ set_action(continue, _St) -> | |
| set_action(undefined, _St) -> | ||
| undefined; | ||
| set_action(sleep, _St) -> | ||
| unset_timer. | ||
| unset_timer; | ||
| set_action({set_timer, Timeout}, _St) -> | ||
| {set_timer, {timeout, Timeout}}. | ||
|
|
||
| call(ID, Call) -> | ||
| case machinery:call(?NS, ID, Call, backend()) of | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
В
dmt_clientтеперь же есть оптимальныйcheckout_object.