{"id":42107566,"url":"https://github.com/bdsqqq/try","last_synced_at":"2026-01-26T13:21:04.513Z","repository":{"id":65850169,"uuid":"601316819","full_name":"bdsqqq/try","owner":"bdsqqq","description":"Don't let the Try Catch Tower of Terror destroy your beautiful one liners.","archived":false,"fork":false,"pushed_at":"2023-10-07T16:56:25.000Z","size":181,"stargazers_count":246,"open_issues_count":5,"forks_count":9,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-08-25T01:58:24.359Z","etag":null,"topics":["async-await","error-handling","promise","typescript"],"latest_commit_sha":null,"homepage":"https://trytm.vercel.app","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/bdsqqq.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-02-13T20:15:15.000Z","updated_at":"2025-08-15T12:28:41.000Z","dependencies_parsed_at":"2024-06-18T18:25:18.298Z","dependency_job_id":"9d1bc4e8-64b1-4321-82ec-73f73915d664","html_url":"https://github.com/bdsqqq/try","commit_stats":{"total_commits":39,"total_committers":3,"mean_commits":13.0,"dds":"0.15384615384615385","last_synced_commit":"392bf8a11dc6f89333392b834ec2ecdf63413701"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/bdsqqq/try","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bdsqqq%2Ftry","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bdsqqq%2Ftry/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bdsqqq%2Ftry/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bdsqqq%2Ftry/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/bdsqqq","download_url":"https://codeload.github.com/bdsqqq/try/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bdsqqq%2Ftry/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28779330,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-26T11:46:04.308Z","status":"ssl_error","status_checked_at":"2026-01-26T11:46:02.664Z","response_time":59,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["async-await","error-handling","promise","typescript"],"created_at":"2026-01-26T13:21:03.868Z","updated_at":"2026-01-26T13:21:04.504Z","avatar_url":"https://github.com/bdsqqq.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Try™\n\nDon't let the Try Catch Tower of Terror destroy your beautiful one liners.\n\n## Usage\n\n```\nnpm install @bdsqqq/try\n```\n\n```TS\n\nimport { trytm } from \"@bdsqqq/try\";\n\nconst mockPromise = () =\u003e {\n  return new Promise\u003cstring\u003e((resolve, _) =\u003e {\n    setTimeout(() =\u003e {\n      resolve(\"hello from promise\");\n    }, 1000);\n  });\n};\n\nconst mockPromiseThatFails = () =\u003e {\n  return new Promise\u003cstring\u003e((_, reject) =\u003e {\n    setTimeout(() =\u003e {\n      reject(new Error(\"hello from promise\"));\n    }, 1000);\n  });\n};\n\nconst [data, error] = await trytm(mockPromise());\nconst [data2, error2] = await trytm(mockPromiseThatFails());\n```\n\n## Why does this exist?\n\nAsync await feels like heaven because it avoids the callback hell or Pyramid of Doom by writing asyncronous code in a line by line format:\n\n```TS\nfunction hell() {\n   step1((a) =\u003e {\n      step2((b) =\u003e {\n         step3((c) =\u003e {\n            // ...\n         })\n      })\n   })\n}\n\nasync function heaven(){\n   const a = await step1();\n   const b = await step2(a);\n   const c = await step3(b);\n   // ...\n}\n\n```\n\nUntil error handling comes into play... Because then you end up with the Try-Catch Tower of Terror, where your beautiful one-liners magically expand to at least 5 lines of code:\n\n```TS\nasync function Terror(){\n   let a;\n   let b;\n   let c;\n\n   try {\n      a = await step1();\n   } catch (error) {\n      handle(error);\n   }\n\n\n   try {\n      b = await step2(a);\n   } catch (error) {\n      handle(error);\n   }\n\n\n   try {\n      c = await step3(b);\n   } catch (error) {\n      handle(error);\n   }\n\n   // ...\n}\n\n```\n\nAn easy solution would be to append the `.catch()` method to the end of each promise:\n\n```TS\n\nasync function easy(){\n   const a = await step1().catch(err =\u003e handle(err));\n   const b = await step2(a).catch(err =\u003e handle(err));\n   const c = await step3(b).catch(err =\u003e handle(err));\n   // ...\n}\n\n```\n\nThis approach solves the issue but can get a bit repetitive, another approach is to create a function that implements one Try Catch to replace all the others:\n\n```TS\n\nimport { trytm } from \"@bdsqqq/try\"\n\nasync function awesome() {\n   const [aData, aError] = await trytm(step1());\n   if(aError) // ...\n\n   const [bData, bError] = await trytm(step2(aData));\n   if(bError) // ...\n\n   const [cData, cError] = await trytm(step3(bData));\n   if(cError) // ...\n\n   // ...\n}\n\n```\n\n### Why does this REALLY exist?\n\nI watched [a fireship short](https://www.youtube.com/watch?v=ITogH7lJTyE) and ended up in a rabbit hole to learn how to publish a NPM package. This is still an interesting pattern to use in your codebase but might be best copy pasted instead of being a dependency.\n\nI'll leave the source code here so you don't have to look for the one .ts file in the /src folder:\n\n```TS\nexport const trytm = async \u003cT\u003e(\n   promise: Promise\u003cT\u003e,\n): Promise\u003c[T, null] | [null, Error]\u003e =\u003e {\n   try {\n      const data = await promise;\n      return [data, null];\n   } catch (throwable) {\n      if (throwable instanceof Error) return [null, throwable];\n\n      throw throwable;\n   }\n};\n```\n\n## Attributions\n\nThis code is blatantly stolen from [a fireship youtube short](https://www.youtube.com/watch?v=ITogH7lJTyE), with minor additions to make `data` infer its typing from the promise passed as an argument.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbdsqqq%2Ftry","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbdsqqq%2Ftry","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbdsqqq%2Ftry/lists"}