[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M6GZS0FMF5B870FS8QQC01XQ":3,"skill-same:01M6GZS0FMF5B870FS8QQC01XQ":74},{"skillNo":4,"name":5,"nameZh":6,"description":7,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":16,"sourceHtmlUrl":17,"categories":18,"keywords":19,"publishedAt":32,"linkOnly":33,"markdownContent":34,"markdownBody":35,"frontMatter":36,"refName":37,"commitSha":38,"skillDirectory":39,"forksCount":40,"repositoryHtmlUrl":41,"repositoryHomepageUrl":6,"ownerHtmlUrl":42,"ownerBlogUrl":43,"ownerDescription":44,"updatedAt":45,"install":46,"resources":59},"01M6GZS0FMF5B870FS8QQC01XQ","recover-failed-payments-with-retry-ladder",null,"Use when involuntary churn from declined cards is bleeding revenue. Times card retries against paycheck and balance cycles and measures the recovered dollars rather than retrying blindly.","jiayaoqijia\u002Fcryptoskill","jiayaoqijia","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F1453879?v=4","01M6GMYTX7Q7S504VC6E756ENR","YQ","01M6GMYV1QKJ1CC75MTTGT9PR0",81,"MIT","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-recover-failed-payments-with-retry-ladder\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-recover-failed-payments-with-retry-ladder\u002FSKILL.md",[],[20,21,22,23,24,25,26,27,28,29,30,31],"payments","with","retry","ladder","recover failed payments with retry ladder","use","card","revenue","churn","retries","balance","when","2026-11-10 10:12:30",false,"---\nname: recover-failed-payments-with-retry-ladder\ndescription: Use when involuntary churn from declined cards is bleeding revenue. Times card retries against paycheck and balance cycles and measures the recovered dollars rather than retrying blindly.\n---\n\n# Recover failed payments with a retry ladder\n\nA card decline is usually a timing accident, not a lost customer. Retry on a schedule aligned to paydays, back off the decline, and measure recovered dollars — not attempts.\n\n## Procedure\n\n1. Classify the decline before retrying: `insufficient_funds` and `try_again_later` are soft (retry); `stolen_card`, `lost_card`, `pickup_card` are hard (never retry); `expired_card` retries only after a card-update ping.\n2. For soft declines schedule 3-4 retries near salary dates, e.g. day +3, +5, +7 from failure, each at a fixed local hour. Salary cycles mean the 1st and the 15th recover best.\n3. Run a card-updater (Visa VAU \u002F Mastercard ABU) before every retry so a reissued card is recovered without customer effort.\n4. Compute recovered dollars from the ledger, not the retry log:\n   `recovered_minor = sum(amount_minor for charge in attempts where attempt_n > 0 and status == 'succeeded')`.\n5. Compute the recovery rate as recovered over failed — `rate = recovered_minor \u002F failed_minor` — and track it per decline reason.\n6. Worked example: a month failed 400,000 minor involuntarily; retries recovered 108,000 minor; rate = 27%. A month later, adding the pre-final-retry email lifts recovery to 39% with no extra retries.\n7. Give up after the ladder: on final failure, move the account to the dunning\u002Fsuspension path. Do not retry forever.\n8. Cap retries per card BIN per day across the whole book so one bad processor day does not draw a network warning.\n9. Report recovered dollars and rate; a lower attempt count with a higher rate is a win, not a regression.\n\n10. Retry the outstanding balance, not the original charge, so a partial recovery is not re-collected in full.\n11. Suppress retries during an active support thread so a retry does not land seconds after the \"we'll retry\" notice.\n12. Log every attempt with the decline code and a processor request id so a dispute is answered from evidence.\n13. Feed recovered dollars back into MRR the month they land and keep a separate involuntary-churn line so the save rate stays honest.\n14. A\u002FB the retry timing (payday versus fixed hour) and keep the variant with the higher recovered dollars, not the higher attempt count.\n15. Recompute the recovery rate net of second-order losses: a recovered payment that later chargebacks is not recovered.\n\n## Pitfalls\n\n- Retrying hard declines (`stolen_card`) is network abuse and flags the merchant ID; classify first.\n- Timing retries at a fixed daily hour ignores payday cycles and leaves recovery on the table.\n- Measuring \"retries sent\" instead of \"dollars recovered\" rewards volume over outcome.\n- No card-updater means reissued cards are never recovered even though the customer is willing to pay.\n- Retrying the same card dozens of times in a month produces duplicate authorisation holds and support tickets.\n\n- Retrying the gross charge after a partial payment double-collects; always retry the residual.\n- A retry that fires while a support email is open reads as aggressive and triggers a chargeback.\n- Recovered dollars booked as new revenue overstate new business and hide involuntary churn.\n- Counting a recovered charge that later chargebacks as a save inflates the rate against reality.\n\n## Verification\n\n    python3 -c \"failed=400000; recovered=108000; print(round(recovered\u002Ffailed*100,1), '%')\"\n    # 27.0 % recovery -> compare against the prior month and per decline reason\n\nReport: recovered dollars, recovery rate, and the split by decline reason, with the number of attempts used.\n","# Recover failed payments with a retry ladder\n\nA card decline is usually a timing accident, not a lost customer. Retry on a schedule aligned to paydays, back off the decline, and measure recovered dollars — not attempts.\n\n## Procedure\n\n1. Classify the decline before retrying: `insufficient_funds` and `try_again_later` are soft (retry); `stolen_card`, `lost_card`, `pickup_card` are hard (never retry); `expired_card` retries only after a card-update ping.\n2. For soft declines schedule 3-4 retries near salary dates, e.g. day +3, +5, +7 from failure, each at a fixed local hour. Salary cycles mean the 1st and the 15th recover best.\n3. Run a card-updater (Visa VAU \u002F Mastercard ABU) before every retry so a reissued card is recovered without customer effort.\n4. Compute recovered dollars from the ledger, not the retry log:\n   `recovered_minor = sum(amount_minor for charge in attempts where attempt_n > 0 and status == 'succeeded')`.\n5. Compute the recovery rate as recovered over failed — `rate = recovered_minor \u002F failed_minor` — and track it per decline reason.\n6. Worked example: a month failed 400,000 minor involuntarily; retries recovered 108,000 minor; rate = 27%. A month later, adding the pre-final-retry email lifts recovery to 39% with no extra retries.\n7. Give up after the ladder: on final failure, move the account to the dunning\u002Fsuspension path. Do not retry forever.\n8. Cap retries per card BIN per day across the whole book so one bad processor day does not draw a network warning.\n9. Report recovered dollars and rate; a lower attempt count with a higher rate is a win, not a regression.\n\n10. Retry the outstanding balance, not the original charge, so a partial recovery is not re-collected in full.\n11. Suppress retries during an active support thread so a retry does not land seconds after the \"we'll retry\" notice.\n12. Log every attempt with the decline code and a processor request id so a dispute is answered from evidence.\n13. Feed recovered dollars back into MRR the month they land and keep a separate involuntary-churn line so the save rate stays honest.\n14. A\u002FB the retry timing (payday versus fixed hour) and keep the variant with the higher recovered dollars, not the higher attempt count.\n15. Recompute the recovery rate net of second-order losses: a recovered payment that later chargebacks is not recovered.\n\n## Pitfalls\n\n- Retrying hard declines (`stolen_card`) is network abuse and flags the merchant ID; classify first.\n- Timing retries at a fixed daily hour ignores payday cycles and leaves recovery on the table.\n- Measuring \"retries sent\" instead of \"dollars recovered\" rewards volume over outcome.\n- No card-updater means reissued cards are never recovered even though the customer is willing to pay.\n- Retrying the same card dozens of times in a month produces duplicate authorisation holds and support tickets.\n\n- Retrying the gross charge after a partial payment double-collects; always retry the residual.\n- A retry that fires while a support email is open reads as aggressive and triggers a chargeback.\n- Recovered dollars booked as new revenue overstate new business and hide involuntary churn.\n- Counting a recovered charge that later chargebacks as a save inflates the rate against reality.\n\n## Verification\n\n    python3 -c \"failed=400000; recovered=108000; print(round(recovered\u002Ffailed*100,1), '%')\"\n    # 27.0 % recovery -> compare against the prior month and per decline reason\n\nReport: recovered dollars, recovery rate, and the split by decline reason, with the number of attempts used.\n",{"name":5,"description":7},"main","3df1d0d67b30ff15236561f8c0f9f06d33f42dfd","skills\u002Fpayments\u002F0xklen-recover-failed-payments-with-retry-ladder",17,"https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia","https:\u002F\u002Feth2030.com","Hardcore infra. Building @alt-research and applied cryptography.","2026-11-13 02:31:19",{"source":8,"skillName":5,"commands":47,"prompt":57,"zipAvailable":58},[48,51,54],{"tool":49,"command":50},"npx","npx skills add jiayaoqijia\u002Fcryptoskill --skill recover-failed-payments-with-retry-ladder",{"tool":52,"command":53},"bunx","bunx skills add jiayaoqijia\u002Fcryptoskill --skill recover-failed-payments-with-retry-ladder",{"tool":55,"command":56},"pnpm","pnpm dlx skills add jiayaoqijia\u002Fcryptoskill --skill recover-failed-payments-with-retry-ladder","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-recover-failed-payments-with-retry-ladder\u002FSKILL.md",true,[60,64,70],{"path":61,"resourceType":61,"resourceTypeDesc":62,"sizeBytes":63,"sourceHtmlUrl":16},"LICENSE","许可证",1063,{"path":65,"resourceType":66,"resourceTypeDesc":67,"sizeBytes":68,"sourceHtmlUrl":69},"SOURCE.md","REFERENCE","参考文档",367,"https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-recover-failed-payments-with-retry-ladder\u002FSOURCE.md",{"path":71,"resourceType":66,"resourceTypeDesc":67,"sizeBytes":72,"sourceHtmlUrl":73},"TRUST.auto.yaml",2217,"https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-recover-failed-payments-with-retry-ladder\u002FTRUST.auto.yaml",[75,103,126,144,157,167],{"skillNo":76,"name":77,"nameZh":6,"description":78,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":79,"sourceHtmlUrl":80,"categories":81,"keywords":82,"publishedAt":32},"01M712C436EQYE43342Q4E7GG1","recipe-performance","Diagnose a specific MetaMask user flow's real-app performance and Sentry critical-user-flow telemetry with deterministic mm-harness recipes. Use for CUF boundaries, cold\u002Fwarm\u002Fbackground-resume behavior, latency regressions, lifecycle tags, duplicate or blocking network requests, long tasks, layout\u002Fpaint cost, screen redraws, React rerenders, or browser trace analysis where tests alone cannot prove the real app.","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fwallets\u002Fmetamask-official-recipe-performance\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fwallets\u002Fmetamask-official-recipe-performance\u002FSKILL.md",[],[83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102],"performance","recipe performance","recipe","mm","sentry","harness","app","deterministic","recipes","flow","cold","critical","analysis","tasks","react","browser","layout","screen","network","metamask",{"skillNo":104,"name":105,"nameZh":6,"description":106,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":107,"licenseFileUrl":108,"sourceHtmlUrl":109,"categories":110,"keywords":111,"publishedAt":32},"01M70XT2F8A5CQZ81JBP98KSW3","mexc-spot-websocket","MEXC Spot WebSocket workflows for public streams, protobuf handling, depth maintenance, listen keys, and private streams without exposing API keys.","Apache-2.0","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Fmncrftfrcnm-mexc-spot-websocket\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Fmncrftfrcnm-mexc-spot-websocket\u002FSKILL.md",[],[112,113,114,115,116,117,118,119,120,121,122,123,124,125],"mexc spot websocket","spot","websocket","api","workflows","public","listen","streams","depth","keys","for","api keys","maintenance","protobuf",{"skillNo":127,"name":128,"nameZh":6,"description":129,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":107,"licenseFileUrl":130,"sourceHtmlUrl":131,"categories":132,"keywords":133,"publishedAt":32},"01M70XT0MBXN3WZY1BKN0CPNKR","mexc-spot-rest","MEXC Spot REST workflows for public data, signed account requests, orders, wallet\u002Fadmin actions, and secure signing without exposing API keys.","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Fmncrftfrcnm-mexc-spot-rest\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Fmncrftfrcnm-mexc-spot-rest\u002FSKILL.md",[],[134,113,135,136,137,138,139,123,122,121,140,141,142,117,143,116,115],"mexc spot rest","REST","admin","signing","Wallet","requests","actions","secure","data","orders",{"skillNo":145,"name":146,"nameZh":6,"description":147,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":107,"licenseFileUrl":148,"sourceHtmlUrl":149,"categories":150,"keywords":151,"publishedAt":32},"01M70XSYSVZ2N0N91XCAR2CAK0","mexc-futures-websocket","MEXC Futures WebSocket workflows for public streams, private account\u002Forder\u002Fposition streams, ping\u002Fpong, subscriptions, and depth maintenance.","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Fmncrftfrcnm-mexc-futures-websocket\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Fmncrftfrcnm-mexc-futures-websocket\u002FSKILL.md",[],[152,153,114,154,155,124,122,156,120,119,117,116],"mexc futures websocket","futures","position","ping","subscriptions",{"skillNo":158,"name":159,"nameZh":6,"description":6,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":160,"sourceHtmlUrl":161,"categories":162,"keywords":163,"publishedAt":32},"01M6H0ZWHVE5W04WG2DKQE2SQC","0xklen-version-and-refresh-sanctions-lists","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-version-and-refresh-sanctions-lists\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-version-and-refresh-sanctions-lists\u002FSKILL.md",[],[164,165,166],"refresh","0xklen version and refresh sanctions lists","version",{"skillNo":168,"name":169,"nameZh":6,"description":170,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":171,"sourceHtmlUrl":172,"categories":173,"keywords":174,"publishedAt":32},"01M6H0Z28Q3R8J0S799GJQWXM3","verify-tests-cover-changed-lines","Use when a PR adds code that the existing suite may not exercise. Measures patch coverage — the share of newly changed lines hit by tests — before approving.","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-verify-tests-cover-changed-lines\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-verify-tests-cover-changed-lines\u002FSKILL.md",[],[175,176,177,178,179,180,181,25,182,183,184],"tests","cover","verify tests cover changed lines","verify","coverage","pr","exercise","patch","code","share"]