-
-
Notifications
You must be signed in to change notification settings - Fork 137
Remove Cloudflare dependency and enhance local/cloadflare-free development support #85
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
…eters I've applied a fix for the tool-calling regression. The problem was that a shallow filter was failing to remove the $schema field from nested parts of the tool's JSON schema, causing the Gemini API to reject the request. I've replaced it with a recursive filter that thoroughly cleans the entire tool definition before sending it to the API. This should resolve the invalid JSON payload error.
i forked my main repo with the fixed issue
Thanks for the PR, will test it out later today. Before I test, does this still work fine with cloudflare? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull Request Overview
This PR introduces standalone Node.js server capability to remove the dependency on Cloudflare infrastructure for local development. The changes enable the project to run as either a Cloudflare Worker or a standard Node.js application.
Key changes:
- Added file-based caching system to replace Cloudflare KV store for local development
- Refactored application setup into a shared module for code reuse between Cloudflare and Node.js environments
- Added new NPM scripts and dependencies for local Node.js server operation
Reviewed Changes
Copilot reviewed 7 out of 9 changed files in this pull request and generated 5 comments.
Show a summary per file
File | Description |
---|---|
src/utils/file-cache.ts | Implements file-based cache to replace Cloudflare KV store for local development |
src/local-server.ts | Creates Node.js server entry point using Hono's node adapter |
src/index.ts | Refactored to use shared app creation function |
src/app.ts | Extracted shared Hono application setup logic from index.ts |
package.json | Added dependencies and scripts for local Node.js development |
README.md | Added documentation for both Cloudflare and standalone Node.js development modes |
.env.template | Added environment variable template for local configuration |
src/utils/file-cache.ts
Outdated
const cacheFilePath = path.join(process.cwd(), '.cache.json'); | ||
|
||
interface Cache { | ||
[key: string]: any; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using 'any' type defeats the purpose of TypeScript. Consider using 'unknown' or a more specific type union like 'string | number | boolean | object'.
[key: string]: any; | |
[key: string]: string | number | boolean | object | null; |
Copilot uses AI. Check for mistakes.
src/utils/file-cache.ts
Outdated
return value; | ||
} | ||
} | ||
return value; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The return type 'any' should be avoided. Consider using generics like 'Promise' or 'Promise' for better type safety.
return value; | |
async get<T>(key: string, type?: 'json'): Promise<T | null> { | |
const cache = await readCache(); | |
const value = cache[key] ?? null; | |
if (type === 'json' && typeof value === 'string') { | |
try { | |
return JSON.parse(value) as T; | |
} catch (e) { | |
// Ignore if not valid JSON | |
return value as T; | |
} | |
} | |
return value as T; |
Copilot uses AI. Check for mistakes.
src/utils/file-cache.ts
Outdated
return value; | ||
}, | ||
|
||
async put(key: string, value: any, options?: { expirationTtl?: number }): Promise<void> { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The 'value' parameter uses 'any' type. Consider using 'unknown' or a more specific type for better type safety.
async put(key: string, value: any, options?: { expirationTtl?: number }): Promise<void> { | |
async put(key: string, value: unknown, options?: { expirationTtl?: number }): Promise<void> { |
Copilot uses AI. Check for mistakes.
src/local-server.ts
Outdated
config(); | ||
|
||
const localEnv: Partial<Env> = { | ||
GEMINI_CLI_KV: fileCache as any, // Use file cache as KV store |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Using 'as any' bypasses type checking. Consider creating a proper type interface that both the KV store and file cache implement, or use a more specific type assertion.
GEMINI_CLI_KV: fileCache as any, // Use file cache as KV store | |
// Define a minimal KVStore interface for type safety | |
interface KVStore { | |
get(key: string): Promise<any>; | |
set(key: string, value: any): Promise<void>; | |
delete(key: string): Promise<void>; | |
// Add other methods as needed | |
} | |
// Load environment variables from .env file | |
config(); | |
const localEnv: Partial<Env> = { | |
GEMINI_CLI_KV: fileCache as KVStore, // Use file cache as KV store |
Copilot uses AI. Check for mistakes.
src/utils/file-cache.ts
Outdated
cache[key] = value; | ||
await writeCache(cache); | ||
if (options?.expirationTtl) { | ||
// console.log(`File cache does not support TTL. Key '${key}' will not expire.`); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Commented-out console.log statements should be removed from production code. If this logging is needed for debugging, consider using a proper logging mechanism or removing it entirely.
// console.log(`File cache does not support TTL. Key '${key}' will not expire.`); |
Copilot uses AI. Check for mistakes.
i FIXED THE TYPE ERRORS
YES IT SHOULD WORK ALL I DID WAS ADDING NEW ENTRY POINT AND THE LOCAL CACHE FILE AND UPDATED THE PACKAGE.JSON FILE TO INCLUDE THE NEW START:LOCAL/BUILD:LOCAL COMMANDS THAT POINT TO THE NEW ENTRY POINT |
THANKS FOR THIS AWESOME PROJECT I PLAN TO USE IT BUT I DONT USE CLOADFLARE I RUN MY OWN VPS ITS JUST FOR TESTING AND PERSONAL USE SO I DONT NEED ALL THE FANCY TECH STACK AND EDGE COMPUTING |
Ah good to know! Yeah I built this around Cloudflare as it is a free way to host this 24/7 so you can use the api everywhere. But I understand some people prefer a fully locally version aswell. Looks good! Can you fix the conflict? Prob just the yarn.lock as there were some dependency updates today. Then I will merge it |
icnludes "@hono/node-server": "^1.18.2", "dotenv": "^17.2.1",
Summary
This pull request introduces a new feature allowing the project to be run as a standalone Node.js server,
completely independent of the Cloudflare stack.
To improve the development experience and remove the dependency on Cloudflare for local
testing, a new standalone server setup has been added.
Changes:
Cloudflare KV store for token management during local development.
src/app.ts file, allowing both the Cloudflare entrypoint (src/index.ts) and the new
Node.s server (src/local-server.ts) to use the same core application logic without
duplication.
with .dev.vars still available for Cloudflare development.
The README.md file has been updated with a new "Running Locally" section that provides
clear instructions on how to run both the original Cloudflare setup (npm run dev) and
the new standalone Node.js setup (npm run start:local).