Convert to TypeScript

- Renamed bring → bring.ts
- Added TypeScript interfaces for type safety
- Added tsconfig.json for TypeScript configuration
- Updated package.json with TypeScript dependencies
- Updated SKILL.md with TypeScript usage instructions
- Added dist/ to .gitignore

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
This commit is contained in:
Carson (Claude Assistant)
2026-03-08 22:38:30 +01:00
co-authored by Claude Sonnet 4.5
parent df53e2f1ed
commit 557280eb0e
5 changed files with 98 additions and 34 deletions
+2
View File
@@ -2,3 +2,5 @@ node_modules/
package-lock.json
*.log
.env
dist/
*.tsbuildinfo
+26 -11
View File
@@ -2,11 +2,21 @@
Manage your Bring! Shopping List via CLI using the unofficial Bring! API.
TypeScript implementation with full type safety.
## Installation
```bash
npm install
chmod +x bring
chmod +x bring.ts
```
Or to build and run as JavaScript:
```bash
npm install
npm run build
node dist/bring.js
```
## Configuration
@@ -63,28 +73,33 @@ console.log(lists.lists); // Shows all lists with their UUIDs
## Commands
```bash
bring add <item> [specification] # Add item to shopping list
bring list # Show current items
bring remove <item> # Remove item (mark as purchased)
bring recent # Show recently purchased items
./bring.ts add <item> [specification] # Add item to shopping list
./bring.ts list # Show current items
./bring.ts remove <item> # Remove item (mark as purchased)
./bring.ts recent # Show recently purchased items
```
Or using ts-node directly:
```bash
ts-node bring.ts add <item>
```
## Examples
```bash
# Add items
bring add Apples
bring add Milk "1 Liter"
bring add "Coffee Beans" "Fair Trade"
./bring.ts add Apples
./bring.ts add Milk "1 Liter"
./bring.ts add "Coffee Beans" "Fair Trade"
# Show list
bring list
./bring.ts list
# Remove item (mark as bought)
bring remove Apples
./bring.ts remove Apples
# Show recently purchased items
bring recent
./bring.ts recent
```
## Integration with AI Agents
+40 -22
View File
@@ -1,14 +1,31 @@
#!/usr/bin/env node
#!/usr/bin/env ts-node
const bringApi = require('bring-shopping');
import BringApi from 'bring-shopping';
interface Credentials {
mail: string;
password: string;
}
interface BringItem {
name: string;
specification: string;
}
interface BringItems {
uuid: string;
status: string;
purchase: BringItem[];
recently: BringItem[];
}
// Load credentials from environment variables
const CREDENTIALS = {
mail: process.env.BRING_EMAIL,
password: process.env.BRING_PASSWORD
const CREDENTIALS: Credentials = {
mail: process.env.BRING_EMAIL || '',
password: process.env.BRING_PASSWORD || ''
};
const LIST_UUID = process.env.BRING_LIST_UUID;
const LIST_UUID: string = process.env.BRING_LIST_UUID || '';
// Validate required environment variables
if (!CREDENTIALS.mail || !CREDENTIALS.password || !LIST_UUID) {
@@ -18,16 +35,16 @@ if (!CREDENTIALS.mail || !CREDENTIALS.password || !LIST_UUID) {
process.exit(1);
}
async function main() {
const args = process.argv.slice(2);
const command = args[0];
async function main(): Promise<void> {
const args: string[] = process.argv.slice(2);
const command: string | undefined = args[0];
if (!command) {
console.error('Usage: bring <add|list|remove|recent> [args...]');
process.exit(1);
}
const bring = new bringApi(CREDENTIALS);
const bring = new BringApi(CREDENTIALS);
try {
await bring.login();
@@ -51,7 +68,8 @@ async function main() {
process.exit(1);
}
} catch (error) {
console.error('Error:', error.message);
const errorMessage = error instanceof Error ? error.message : 'Unknown error';
console.error('Error:', errorMessage);
process.exit(1);
}
}
@@ -59,9 +77,9 @@ async function main() {
/**
* Add an item to the shopping list
*/
async function addItem(bring, args) {
const itemName = args[0];
const specification = args.slice(1).join(' ') || '';
async function addItem(bring: any, args: string[]): Promise<void> {
const itemName: string | undefined = args[0];
const specification: string = args.slice(1).join(' ') || '';
if (!itemName) {
console.error('Usage: bring add <item> [specification]');
@@ -80,8 +98,8 @@ async function addItem(bring, args) {
/**
* List all items currently on the shopping list
*/
async function listItems(bring) {
const items = await bring.getItems(LIST_UUID);
async function listItems(bring: any): Promise<void> {
const items: BringItems = await bring.getItems(LIST_UUID);
if (items.purchase.length === 0) {
console.log('Shopping list is empty');
@@ -90,7 +108,7 @@ async function listItems(bring) {
console.log('Shopping list:');
console.log('');
items.purchase.forEach((item, index) => {
items.purchase.forEach((item: BringItem, index: number) => {
if (item.specification) {
console.log(`${index + 1}. ${item.name} (${item.specification})`);
} else {
@@ -102,8 +120,8 @@ async function listItems(bring) {
/**
* Remove an item from the shopping list (mark as purchased)
*/
async function removeItem(bring, args) {
const itemName = args.join(' ');
async function removeItem(bring: any, args: string[]): Promise<void> {
const itemName: string = args.join(' ');
if (!itemName) {
console.error('Usage: bring remove <item>');
@@ -117,8 +135,8 @@ async function removeItem(bring, args) {
/**
* Show recently purchased items
*/
async function recentItems(bring) {
const items = await bring.getItems(LIST_UUID);
async function recentItems(bring: any): Promise<void> {
const items: BringItems = await bring.getItems(LIST_UUID);
if (items.recently.length === 0) {
console.log('No recently purchased items');
@@ -127,7 +145,7 @@ async function recentItems(bring) {
console.log('Recently purchased:');
console.log('');
items.recently.slice(0, 10).forEach((item, index) => {
items.recently.slice(0, 10).forEach((item: BringItem, index: number) => {
if (item.specification) {
console.log(`${index + 1}. ${item.name} (${item.specification})`);
} else {
+11 -1
View File
@@ -1,8 +1,18 @@
{
"name": "bring-shopping-skill",
"version": "1.0.0",
"description": "Bring! Shopping List Skill for Carson",
"description": "Bring! Shopping List Skill - TypeScript CLI",
"type": "module",
"scripts": {
"build": "tsc",
"start": "ts-node bring.ts"
},
"dependencies": {
"bring-shopping": "^2.0.1"
},
"devDependencies": {
"@types/node": "^20.0.0",
"ts-node": "^10.9.0",
"typescript": "^5.0.0"
}
}
+19
View File
@@ -0,0 +1,19 @@
{
"compilerOptions": {
"target": "ES2020",
"module": "commonjs",
"lib": ["ES2020"],
"outDir": "./dist",
"rootDir": "./",
"strict": true,
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true,
"resolveJsonModule": true,
"declaration": true,
"declarationMap": true,
"sourceMap": true
},
"include": ["*.ts"],
"exclude": ["node_modules", "dist"]
}