ð¥Honoã䜿ã£ãŠCloudflare Workersã¢ããªãæžãæããŠã¿ã
Hono
ãšãããã¬ãŒã ã¯ãŒã¯ãæ°ã«ãªã£ãŠããã®ã§äœ¿ã£ãŠã¿ãŸããã
æ°ã«ãªã£ãŠããçç±ã¯ãååãçŽ æµã ããã§ãç¬
4æåã§ãããã«ãªã®ãè¯ãã§ããã
ãªããšãªããŠã©ããããŠããã®ã§ãããæ°ã¥ãããããªã人æ°ã®ãã¬ãŒã ã¯ãŒã¯ã«ãªã£ãŠããŸããã
ð¥Honoãšã¯
Cloudflare Workers
äžã§åããããšãç®çã«äœããã軜éãªWebãã¬ãŒã ã¯ãŒã¯ã§ãã
Hono - [ç] means flameð¥ in Japanese - is a small, simple, and ultrafast web framework for the Edge. It works on Cloudflare Workers, Fastly Compute@Edge, Deno, Bun, Vercel, Lagon, Node.js, and others. Fast, but not only fast.
ãã®èª¬æèªãã æã«ãããªãšæã£ãŠããã€ã䜿ããããªãšæã£ãŠãŸããð
ã¡ãªã¿ã«ãCloudflare Workers
ã¯ãCDNïŒã³ã³ãã³ãããªããªãŒãããã¯ãŒã¯ïŒã®ãšããžäžã§JavaScriptã³ãŒããå®è¡ã§ãããã®ã§ãã
ãšãŠãé«éã§ãããããããã€ãããªãç°¡åã«çŽ æ©ãã§ãããšããããšã§ãã¡ãã£ãšããAPIãäœæããã®ã«æè¿ãã䜿ãããŠããŸãã
ä»åãã£ãããš
ä»åã¯Cloudflare Workers
ã§åãããŠããAPIãããã®ã§ããããHono
ã§æžãçŽããŠã¿ãŸããã
ãã¡ãã®ãããã¯ãã§ãã
APIãïŒã€ã ãã®ç°¡åãªãããã¯ãã«ãªããŸãã
䜿ãæ¹
READMEéãã§ããã
npm create hono@latest my-app
ãšããã°ç©ºã®ã¢ããªãã§ããŸãã
åã¯ãã§ã«æ¢åã³ãŒãããã£ãã®ã§ãããžã§ã¯ãã®ãã£ã¬ã¯ããªäžã§ã
npm create hono@latest .
ãšããŠäžæžãããŠãå¿ èŠãªãã®ãpushããŠããGitHubãªããžããªããã³ããŒããŠããŸããã
æžãæããéšå
äž»ã«äžèšã«ãªããŸãã
- package.json
- ç°å¢å€æ°ååŸéšå
- fetché¢æ°âã«ãŒãã£ã³ã°
1. package.json
ãŸã£ããã«ãªã£ãŠããã®ã§ãå ã 䜿ã£ãŠããã©ã€ãã©ãªé¡ãè¿œå ããŸãã
2. ç°å¢å€æ°ååŸéšå
ç°å¢å€æ°ã®ååŸæ¹æ³ãå€ãã£ãŠããã®ã§æžãæããŸãã
Honoã§ã¯interfaceãå®çŸ©ããå¿
èŠããªããªã£ãŠããŸãã
// å®çŸ©
export interface Env {
TWITTER_BEARER_TOKEN: string;
OPENAI_ORGANIZATION: string;
OPENAI_API_KEY: string;
}
// 䜿ãå Žæ
const client = new Client(env.TWITTER_BEARER_TOKEN);
âââ
app.get("/", async (c) => {
const text = await getTweetTextById(
// å®çŸ©ã¯äžèŠã§ãã®ãŸãŸäœ¿ãã
c.env!.TWITTER_BEARER_TOKEN as string,
tweetId
);
tsãšã©ãŒã«ãªãã®ã§ã!
ãas string
ãä»ããŠããã§ããã©ãããã¥ã¡ã³ãã§ã¯ä»ããŠããªããã§ãããããã¬ãŒã ã¯ãŒã¯ãšçŽæ¥é¢ä¿ãªãã§ãããtsåã匱ãããããããªãéšåã§ããã
3. fetché¢æ°âã«ãŒãã£ã³ã°
Cloudflare Workers
ã¯ãªã¯ãšã¹ããåãããšfetché¢æ°ãåŒã°ãããšããä»çµã¿ã§ããHono
ã§ã¯ã«ãŒãã£ã³ã°ã®ä»çµã¿ãããã®ã§ããã®ããã«å®è£
ããŸãã
export default {
async fetch(request) {
return new Response(html);
},
};
âââ
import { Hono } from 'hono'
const app = new Hono()
app.get('/', (c) => c.text('Hono!'))
export default app
æžãæããã³ãããã¯ãã¡ãã§ãã
ã¡ãã£ãšå°ã£ãããš
æ¢åã³ãŒãã§ã¯ãåŠçããšã«é¢æ°åããŠããŸããã
ãã®é¢æ°ã«Cloudflare Workers
ã§äœ¿ãããRequestãEnvãæž¡ããŠããŸããã
Hono
ã§ãåãããã«ïŒãªãã¹ãå
ã®æ§æãå€ããããªãã£ãã®ã§ïŒãContextãé¢æ°ã«æž¡ããããªãšæããŸããã
ããããé¢æ°åŽã«ã©ã®ãããªåå®çŸ©ãããã°ããã®ããããããtsåã®ç¡ããçæããŸããã
ããããã®ã¯ããããããšã§ãããšæ¹ããŠæžããŠã¿ããåºæ¥ãŸãããã
ãã ã"/sample"
ãšpathãåã«æååã§æžãã®ã¯ãããããã®ãªãã ãããããšãããšããããŸã ç解ãæµ
ãéšåã§ããã¡ãããšç解ããŠããããéšåã§ãã
ãŸãšã
ç°¡åã§ãããð¥Hono
ã䜿ã£ãŠã¿ã玹ä»ã§ããã
ä»åã¯APIãïŒã€ã ãã ã£ãã®ã§ããŸãã¡ãªããã¯ãªãã§ãããã«ãŒãã£ã³ã°ãç°¡åã«ã§ããã®ã¯ãšãŠãé
åçã§ãããããããªããšèªåã§URLãèŠãŠåãæ¿ããªããã°ãããªãã®ã§ã
䜿ãæ¹ããšãŠãããããã§ããã
次ã¯ãã®ãããã¯ãã«ç»é¢ãäžã€è¿œå ããããªãšæã£ãŠããŸãã
ããã¹ããåãä»ããŠçµæãè¿ãç°¡åãªãã©ãŒã ã§ãã
HTMLçŽã§æžãã®ã¯ã¡ãã£ãšãªããšæã£ãŠãããJSX Middleware
ãšããã®ãèŠã€ããã®ã§ãããã䜿ã£ãŠã¿ãããšæããŸãã
Reactã§äœ¿ãããŠããJSX syntax
ãHono
ã§äœ¿ããããã«ãããã®ã§ãã
Cloudflare Workers
&Hono
ã䜿ããããã«ããŠãããšãã¡ãã£ãšãããã®ãããã£ãšäœã£ãŠå
¬éã§ããã®ã§ãšãŠã䟿å©ã§ãã
ã¿ãªããããã²äœ¿ã£ãŠã¿ãŠãã ããã
Discussion
ããã«ã¡ãïŒHonoã®äœè ã§ãã䜿ã£ãŠãããŠããããšãããããŸãïŒïŒããã¥ã¡ã³ããäžååã ã£ããããŠããããã«ããã£ãããã§ãããããã€ãæ°ã¥ããã®ã§è£è¶³ãããŠãã ããã
ãŸããç°å¢å€æ°ã§ãããHonoã䜿ãã䜿ããªããã«é¢ããããåå®çŸ©ãªããšãå€ã¯ååŸã§ããŸããHonoã®å Žåã¯ä»¥äžã®ããã«Typeãæž¡ãããšã§ãè£å®ãå¹ãããã«ãªããŸãã
ã¯ãšãªã®ããŒã¹ã¯
c.req.query()
ã䜿ãã°ç°¡åã«ã§ããŸãã次ã«ããã³ãã©ã®äžãtry/catchã§å²ã£ãŠããããã§ããã Honoã¯ãšã©ãŒã®ãã³ããªã³ã°ãèªåã§ããã®ã§ããšããããã®å¿ èŠã¯ãªããšæããŸãã
ãŸãã
new Response('..')
ããŠããšããã¯ãc.text()
ãªã©ã®ã·ã§ãŒãã«ããã䜿ããŸãïŒããã¯Honoé¢ä¿ãªããªã£ã¡ãããŸãããCloudflare Workersã§ã¯Web Standardã®APIã䜿ããã®ã§ã¯ãšãªãã©ã¡ãŒã¿ã®äœæãªã©ã¯URLSearchParamsã䜿ããšãããã§ãã
èªåãªãã«ãªãã¡ã¯ã¿ããã³ãŒãã¯ä»¥äžã«ãªããŸãã
ãªããè²ã ã³ã¡ã³ãããŠãããŸãããããã¥ã¡ã³ããåãããããããã®ãšãå¢ããã®ããã°ããŸãïŒ
ããŒãè²ã ãšã³ã¡ã³ãããããšãããããŸãïŒ
Honoã¯yusukebeããã®TwitterèŠãŠãã£ãšæ°ã«ãªã£ãŠãã®ã§ã³ã¡ã³ãããããŠå¬ããã§ãïŒ
ãªãã¡ã¯ã¿ããã³ãŒããŸã§ããããšãããããŸãã
åèã«æžãçŽããŠã¿ãŸãð