[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M6H0178WKPJM4CWH2E3F2J6D":3,"skill-same:01M6H0178WKPJM4CWH2E3F2J6D":80},{"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":38,"linkOnly":39,"markdownContent":40,"markdownBody":41,"frontMatter":42,"refName":43,"commitSha":44,"skillDirectory":45,"forksCount":46,"repositoryHtmlUrl":47,"repositoryHomepageUrl":6,"ownerHtmlUrl":48,"ownerBlogUrl":49,"ownerDescription":50,"updatedAt":51,"install":52,"resources":65},"01M6H0178WKPJM4CWH2E3F2J6D","roll-out-a-canary-release",null,"Use when a change is too risky for an all-at-once deploy — routes a small traffic slice to the new version, gates promotion on SLO comparison against stable, and reverts on regression.","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-roll-out-a-canary-release\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-roll-out-a-canary-release\u002FSKILL.md",[],[20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37],"release","canary","roll out a canary release","comparison","new","when","slice","for","at","traffic","promotion","change","gates","slo","version","use","regression","deploy","2026-11-10 10:12:30",false,"---\nname: roll-out-a-canary-release\ndescription: Use when a change is too risky for an all-at-once deploy — routes a small traffic slice to the new version, gates promotion on SLO comparison against stable, and reverts on regression.\n---\n\n# Roll out a canary release\n\nShip to 1% of traffic first. Compare the canary's error rate and latency against the stable version on the same traffic mix, and promote only if the canary is not worse. This catches the regressions that pass every pre-production test.\n\n## Procedure\n\n1. Route by a stable key (user-id hash, header, or mesh weight) so a user's experience is consistent within the canary, not round-robin per request:\n       # Istio VirtualService\n       http: [{ route: [ {destination: {host: app, subset: stable},  weight: 99},\n                          {destination: {host: app, subset: canary}, weight: 1 } ] }]\n\n2. Size the canary so the sample is meaningful: at least 1000 requests and 30 minutes before judging. At 1% of 100 rps that is about 17 minutes of traffic.\n\n3. Compare against stable measured *at the same time*, never against yesterday — the traffic mix shifts daily:\n       canary_err = rate(err{version=\"canary\"}[5m]) \u002F rate(req{version=\"canary\"}[5m])\n       stable_err = rate(err{version=\"stable\"}[5m]) \u002F rate(req{version=\"stable\"}[5m])\n\n4. Promotion gates, all must hold: canary error ratio ≤ stable + 0.2 pp, canary p99 ≤ stable × 1.1, no error code new to the canary, canary saturation \u003C 0.8.\n\n5. Step the weight 1 → 5 → 25 → 50 → 100, holding each step at least 15 minutes and re-checking the gates. On any breach, set the canary weight to 0 immediately and keep the pods for logs.\n\n6. Automate the gate with Argo Rollouts `AnalysisTemplate` or Flagger so promotion is not a human watching a dashboard at 2 a.m.\n\n7. Run the canary long enough to catch slow leaks — memory, file descriptors, goroutines — which all pass a 15-minute latency check.\n\n## Pitfalls\n\n- Judging on too little traffic: 20 requests give a meaningless ratio and the gate flaps.\n- Comparing the canary with yesterday's stable, so a global regression looks like a canary-only win.\n- A canary that differs from stable in more than the code (different config or replica count) — you are then measuring the wrong variable.\n- A new error path affecting only a specific customer segment, hidden by the aggregate ratio; break down by `code` and by `route`.\n\n## Verification\n\n    kubectl argo rollouts get rollout app --watch\n    # steps advance only while analysis passes; setWeight 0 on failure\n    curl -s 'localhost:9090\u002Fapi\u002Fv1\u002Fquery?query=sum(rate(err{version=\"canary\"}[5m]))\u002Fsum(rate(req{version=\"canary\"}[5m]))' | jq\n\nReport: the weight schedule, the gate thresholds, the canary-vs-stable error and p99 deltas at each step, and either promotion or the timestamped revert.\n","# Roll out a canary release\n\nShip to 1% of traffic first. Compare the canary's error rate and latency against the stable version on the same traffic mix, and promote only if the canary is not worse. This catches the regressions that pass every pre-production test.\n\n## Procedure\n\n1. Route by a stable key (user-id hash, header, or mesh weight) so a user's experience is consistent within the canary, not round-robin per request:\n       # Istio VirtualService\n       http: [{ route: [ {destination: {host: app, subset: stable},  weight: 99},\n                          {destination: {host: app, subset: canary}, weight: 1 } ] }]\n\n2. Size the canary so the sample is meaningful: at least 1000 requests and 30 minutes before judging. At 1% of 100 rps that is about 17 minutes of traffic.\n\n3. Compare against stable measured *at the same time*, never against yesterday — the traffic mix shifts daily:\n       canary_err = rate(err{version=\"canary\"}[5m]) \u002F rate(req{version=\"canary\"}[5m])\n       stable_err = rate(err{version=\"stable\"}[5m]) \u002F rate(req{version=\"stable\"}[5m])\n\n4. Promotion gates, all must hold: canary error ratio ≤ stable + 0.2 pp, canary p99 ≤ stable × 1.1, no error code new to the canary, canary saturation \u003C 0.8.\n\n5. Step the weight 1 → 5 → 25 → 50 → 100, holding each step at least 15 minutes and re-checking the gates. On any breach, set the canary weight to 0 immediately and keep the pods for logs.\n\n6. Automate the gate with Argo Rollouts `AnalysisTemplate` or Flagger so promotion is not a human watching a dashboard at 2 a.m.\n\n7. Run the canary long enough to catch slow leaks — memory, file descriptors, goroutines — which all pass a 15-minute latency check.\n\n## Pitfalls\n\n- Judging on too little traffic: 20 requests give a meaningless ratio and the gate flaps.\n- Comparing the canary with yesterday's stable, so a global regression looks like a canary-only win.\n- A canary that differs from stable in more than the code (different config or replica count) — you are then measuring the wrong variable.\n- A new error path affecting only a specific customer segment, hidden by the aggregate ratio; break down by `code` and by `route`.\n\n## Verification\n\n    kubectl argo rollouts get rollout app --watch\n    # steps advance only while analysis passes; setWeight 0 on failure\n    curl -s 'localhost:9090\u002Fapi\u002Fv1\u002Fquery?query=sum(rate(err{version=\"canary\"}[5m]))\u002Fsum(rate(req{version=\"canary\"}[5m]))' | jq\n\nReport: the weight schedule, the gate thresholds, the canary-vs-stable error and p99 deltas at each step, and either promotion or the timestamped revert.\n",{"name":5,"description":7},"main","3df1d0d67b30ff15236561f8c0f9f06d33f42dfd","skills\u002Fpayments\u002F0xklen-roll-out-a-canary-release",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-15 02:28:10",{"source":8,"skillName":5,"commands":53,"prompt":63,"zipAvailable":64},[54,57,60],{"tool":55,"command":56},"npx","npx skills add jiayaoqijia\u002Fcryptoskill --skill roll-out-a-canary-release",{"tool":58,"command":59},"bunx","bunx skills add jiayaoqijia\u002Fcryptoskill --skill roll-out-a-canary-release",{"tool":61,"command":62},"pnpm","pnpm dlx skills add jiayaoqijia\u002Fcryptoskill --skill roll-out-a-canary-release","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-roll-out-a-canary-release\u002FSKILL.md",true,[66,70,76],{"path":67,"resourceType":67,"resourceTypeDesc":68,"sizeBytes":69,"sourceHtmlUrl":16},"LICENSE","许可证",1063,{"path":71,"resourceType":72,"resourceTypeDesc":73,"sizeBytes":74,"sourceHtmlUrl":75},"SOURCE.md","REFERENCE","参考文档",351,"https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-roll-out-a-canary-release\u002FSOURCE.md",{"path":77,"resourceType":72,"resourceTypeDesc":73,"sizeBytes":78,"sourceHtmlUrl":79},"TRUST.auto.yaml",2217,"https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fpayments\u002F0xklen-roll-out-a-canary-release\u002FTRUST.auto.yaml",[81,109,131,149,162,171],{"skillNo":82,"name":83,"nameZh":6,"description":84,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":85,"sourceHtmlUrl":86,"categories":87,"keywords":88,"publishedAt":38},"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",[],[89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108],"performance","recipe performance","recipe","mm","sentry","harness","app","deterministic","recipes","flow","cold","critical","analysis","tasks","react","browser","layout","screen","network","metamask",{"skillNo":110,"name":111,"nameZh":6,"description":112,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":113,"licenseFileUrl":114,"sourceHtmlUrl":115,"categories":116,"keywords":117,"publishedAt":38},"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",[],[118,119,120,121,122,123,124,125,126,127,27,128,129,130],"mexc spot websocket","spot","websocket","api","workflows","public","listen","streams","depth","keys","api keys","maintenance","protobuf",{"skillNo":132,"name":133,"nameZh":6,"description":134,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":113,"licenseFileUrl":135,"sourceHtmlUrl":136,"categories":137,"keywords":138,"publishedAt":38},"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",[],[139,119,140,141,142,143,144,128,27,127,145,146,147,123,148,122,121],"mexc spot rest","REST","admin","signing","Wallet","requests","actions","secure","data","orders",{"skillNo":150,"name":151,"nameZh":6,"description":152,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":113,"licenseFileUrl":153,"sourceHtmlUrl":154,"categories":155,"keywords":156,"publishedAt":38},"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",[],[157,158,120,159,160,129,27,161,126,125,123,122],"mexc futures websocket","futures","position","ping","subscriptions",{"skillNo":163,"name":164,"nameZh":6,"description":6,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":165,"sourceHtmlUrl":166,"categories":167,"keywords":168,"publishedAt":38},"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",[],[169,170,34],"refresh","0xklen version and refresh sanctions lists",{"skillNo":172,"name":173,"nameZh":6,"description":174,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":175,"sourceHtmlUrl":176,"categories":177,"keywords":178,"publishedAt":38},"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",[],[179,180,181,182,183,184,185,35,186,187,188],"tests","cover","verify tests cover changed lines","verify","coverage","pr","exercise","patch","code","share"]