{"id":29471985,"url":"https://github.com/refinist/hono-json-response","last_synced_at":"2025-07-14T14:04:49.341Z","repository":{"id":297817739,"uuid":"997981141","full_name":"refinist/hono-json-response","owner":"refinist","description":"🔥 A Hono middleware for standardized JSON responses","archived":false,"fork":false,"pushed_at":"2025-06-08T05:27:40.000Z","size":61,"stargazers_count":23,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-07-08T10:37:31.399Z","etag":null,"topics":["api","framework","hono","http","json","middleware","response","typescript","web"],"latest_commit_sha":null,"homepage":"","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/refinist.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,"zenodo":null}},"created_at":"2025-06-07T16:03:59.000Z","updated_at":"2025-06-29T14:46:29.000Z","dependencies_parsed_at":"2025-06-07T17:43:30.215Z","dependency_job_id":null,"html_url":"https://github.com/refinist/hono-json-response","commit_stats":null,"previous_names":["refinist/hono-json-response"],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/refinist/hono-json-response","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/refinist%2Fhono-json-response","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/refinist%2Fhono-json-response/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/refinist%2Fhono-json-response/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/refinist%2Fhono-json-response/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/refinist","download_url":"https://codeload.github.com/refinist/hono-json-response/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/refinist%2Fhono-json-response/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":265304536,"owners_count":23743880,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","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":["api","framework","hono","http","json","middleware","response","typescript","web"],"created_at":"2025-07-14T14:02:23.836Z","updated_at":"2025-07-14T14:04:49.324Z","avatar_url":"https://github.com/refinist.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# \u003cimg src=\"https://hono.dev/images/logo.svg\" width=\"24\" height=\"24\" /\u003e Hono jsonResponse Middleware [![npm](https://img.shields.io/npm/v/hono-json-response.svg?style=flat\u0026colorA=E36002\u0026colorB=FF9C24)](https://npmjs.com/package/hono-json-response) [![codecov](https://img.shields.io/codecov/c/github/refinist/hono-json-response?style=flat\u0026colorA=E36002\u0026colorB=FF9C24)](https://codecov.io/github/refinist/hono-json-response)\n\nA Hono middleware for standardized JSON responses\n\n## Why Choose This Middleware?\n\n### ❌ Traditional Approach: Repetitive and Error-Prone\n\n```typescript\nreturn c.json({ code: 2000, data: users, msg: 'Operation successful' });\nreturn c.json({ code: 2000, data: roles, msg: 'Operation successful' });\nreturn c.json({ code: 5000, data: null, msg: 'Username already exists' });\nreturn c.json({ code: 5100, data: null, msg: 'System error' });\n```\n\n### ✅ Using Middleware: Semantic and Concise\n\n```typescript\nreturn c.ok(users, 'Operation successful');\nreturn c.ok(roles); // No need to pass \"Operation successful\" every time, as it's the default\nreturn c.bizerr(null, 'Username already exists');\nreturn c.syserr();\n```\n\n## Features\n\n- 🚀 **Unified JSON Response Format** - Standardized API response structure\n- 🎯 **Semantic Response Methods** - `c.ok()` is more intuitive than `c.json({code: 2000})`\n- 🔧 **Eliminate Boilerplate Code** - Say goodbye to repetitive `c.json({code: xxx, data: xxx, msg: xxx})` patterns\n- 📝 **Predefined Common Scenarios** - ok(success), unauth(unauthorized), bizerr(business error), syserr(system error)\n- 🛠️ **Flexible Extension** - Support for custom response methods and status codes\n- 💪 **Type Safety** - Complete TypeScript support and intelligent hints\n\n## Install\n\n```bash\n# npm\nnpm install hono-json-response\n\n# yarn\nyarn add hono-json-response\n\n# pnpm\npnpm add hono-json-response\n\n# bun\nbun add hono-json-response\n```\n\n## Basic Usage\n\n```typescript\nimport { Hono } from 'hono';\nimport { jsonResponse } from 'hono-json-response';\n\nconst app = new Hono();\napp.use('*', jsonResponse());\napp.get('/getUserList', c =\u003e {\n  return c.ok(\n    {\n      list: [{ name: 'John' }, { name: 'Jane' }],\n      totals: 100\n    },\n    'Get user list successfully'\n  );\n});\n```\n\n## Response Format\n\n### Default Format\n\nAll responses follow a unified JSON format (code, data, msg):\n\n```json\n{\n  \"code\": 2000,\n  \"data\": null,\n  \"msg\": \"\"\n}\n```\n\n### Custom Field Names\n\nSupport custom response field names to adapt to different project API specifications:\n\n```ts\napp.use(\n  '*',\n  jsonResponse(null, {\n    code: 'status', // code -\u003e status\n    data: 'result', // data -\u003e result\n    msg: 'message' // msg -\u003e message\n  })\n);\n```\n\n## Predefined Methods\n\n### `c.ok(data?, msg?)`\n\nSuccess response\n\n- **Status Code**: 2000\n- **Usage**: When operation is successful\n\n```ts\napp.get('/getUserList', c =\u003e {\n  return c.ok(\n    {\n      list: [{ name: 'John' }, { name: 'Jane' }],\n      totals: 100\n    },\n    'Get user list successfully'\n  );\n});\n```\n\n### `c.unauth(data?, msg?)`\n\nUnauthorized response\n\n- **Status Code**: 4000\n- **Usage**: When user is not logged in or token is invalid\n\n```ts\napp.post('/login', c =\u003e {\n  return c.unauth();\n});\n```\n\n### `c.bizerr(data?, msg?)`\n\nBusiness error response\n\n- **Status Code**: 5000\n- **Usage**: Business logic errors (such as duplicate accounts, insufficient inventory, etc.)\n\n```ts\napp.post('/register', async c =\u003e {\n  const { name } = await c.req.json();\n  return c.bizerr({ name }, `Username ${name} already exists`);\n});\n```\n\n### `c.syserr(data?, msg?)`\n\nSystem error response\n\n- **Status Code**: 5100\n- **Usage**: System-level errors (such as database connection failure, processing exceptions, etc.)\n\n```ts\napp.post('/foo', c =\u003e {\n  try {\n    // do something\n  } catch (error) {\n    return c.syserr(error);\n  }\n});\n```\n\n### `c.jr(code, data?, msg?)`\n\nCustom response code\n\n- **Parameter**: code - Custom status code\n- **Usage**: Some complex interfaces may need to return more status codes to represent different business logic\n\n```ts\napp.get('/orders/:id', async c =\u003e {\n  const orderId = c.req.param('id');\n\n  try {\n    const order = await getOrderById(orderId);\n\n    // Order not found\n    if (!order) {\n      return c.jr(5000, null, 'Order not found');\n    }\n\n    // No permission to access other user's order\n    if (order.userId !== userId) {\n      return c.jr(5001, null, 'No permission to access this order');\n    }\n\n    // Order has been deleted\n    if (order.status === 'deleted') {\n      return c.jr(5002, null, 'Order has been deleted');\n    }\n    // More business logic...\n\n    return c.ok(order, 'Get order details successfully');\n  } catch (error) {\n    return c.syserr(null, 'Failed to get order details');\n  }\n});\n```\n\n## Custom Configuration\n\n### Override Default Configuration\n\n```typescript\napp.use(\n  '*',\n  jsonResponse({\n    ok: { code: 20000, defaultMsg: 'Override ok' },\n    unauth: { code: 40000, defaultMsg: 'Override unauth' }\n  })\n);\n```\n\n### Add Custom Methods\n\n```typescript\nimport type { JSONResponseHandler } from 'hono-json-response';\n\n// Don't forget to use TypeScript module augmentation to extend Context type\ndeclare module 'hono' {\n  interface Context {\n    warning: JSONResponseHandler;\n    forbidden: JSONResponseHandler;\n  }\n}\n\napp.use(\n  '*',\n  jsonResponse({\n    warning: { code: 2001, defaultMsg: 'Warning message' },\n    forbidden: { code: 4001, defaultMsg: 'Access forbidden' }\n  })\n);\n\napp.get('/warning', c =\u003e {\n  return c.warning(data, 'API will be deprecated');\n});\n```\n\n### Handle Status Code Conflicts\n\nWhen custom method status codes conflict with default methods, default methods will be automatically removed:\n\n```typescript\napp.use(\n  '*',\n  jsonResponse({\n    mySuccess: { code: 2000 } // Conflicts with default ok method\n  })\n);\n\n// At this point, c.ok method is no longer available, only c.mySuccess is available\n```\n\n## License\n\n[MIT](./LICENSE)\n\nCopyright (c) 2025-present, Zhifeng (Jeff) Wang\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frefinist%2Fhono-json-response","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Frefinist%2Fhono-json-response","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frefinist%2Fhono-json-response/lists"}