npm package: @flashaim-gmb/startupbase-draft
Description: Common interface for front-end and back-end
Author: kevin@flashaim.com
Latest version: 0.0.7

# 📝 StartupBase Draft - 共用介面定義

StartupBase 專案的共用型別定義套件，提供前端和後端之間的介面規範，確保資料結構的一致性。

## 📦 套件資訊

- **名稱**: `@flashaim-gmb/startupbase-draft`
- **版本**: 0.0.5
- **描述**: 前後端共用介面定義
- **作者**: kevin@flashaim.com
- **授權**: MIT

## 🎯 設計目標

### 型別安全
- 提供 TypeScript 型別定義
- 確保前後端資料結構一致
- 減少型別錯誤和執行時錯誤

### 程式碼重用
- 避免重複定義相同介面
- 統一資料驗證邏輯
- 簡化維護成本

### 版本控制
- 獨立的版本管理
- 向後相容性保證
- 清楚的變更紀錄

## 🏗️ 核心介面

### 基礎介面

#### `DBbase`
```typescript
export interface DBbase {
    created_at?: number;    // 建立時間戳
    updated_at?: number;    // 更新時間戳
    deleted_at?: number;    // 刪除時間戳 (軟刪除)
}
```

所有資料庫實體的基礎介面，提供統一的時間戳記欄位。

### 草稿系統

#### `DraftType`
```typescript
export type DraftType = 
    | 'office'      // 辦公室租賃
    | 'houseShort'  // 住宅短租
    | 'houseLong'   // 住宅長租
    | 'appoint'     // 委任書
    | 'address'     // 借址合約
    | 'trademark'   // 商標委任書
    | 'website'     // 網站設計合約
    | 'other';      // 其他合約
```

#### `DraftBase`
```typescript
export interface DraftBase extends DBbase {
    id?: string;                    // 草稿 ID
    type: DraftType;                // 草稿類型
    creator_uid: string;            // 建立者 UID
    reviewer_uid?: string;          // 審核者 UID
    status: DraftStatus;            // 草稿狀態
    rejectionReason?: string;       // 駁回原因
    reviewDate?: number;            // 審核日期
    contractNumber?: string;        // 合約編號
    taskId?: number;                // 點點簽任務 ID
    creator?: any;                  // 建立者資訊
    originalDraftId?: string;       // 原草稿 ID (續約用)
    renewedDraftId?: string;        // 續約草稿 ID
    cardRef?: string;               // 付款卡參考路徑
    fileMissionLogId?: string;      // 合併任務紀錄 ID
    mergeUserId?: string;           // 合併用戶 ID
}
```

#### 草稿狀態
```typescript
type DraftStatus = 
    | '資料待填寫'    // 初始狀態
    | '合約處理中'    // 處理中
    | '主管駁回合約'  // 被駁回
    | '合約已審核'    // 審核通過
    | '合約送合併'    // 送合併
    | '合約已發送'    // 已發送
    | '合約已簽署'    // 已簽署
    | '合約終止';     // 已終止
```

### 具體草稿類型

#### 辦公室租賃合約
```typescript
export interface OfficeDraft extends DraftBase {
    name: '辦公室租賃合約';
    type: 'office';
    draftDetail: OfficeDraftDetail;
}
```

#### 借址合約
```typescript
export interface AddressDraft extends DraftBase {
    name: '借址合約';
    type: 'address';
    draftDetail: AddressDraftDetail;
}
```

#### 住宅租賃合約
```typescript
export interface HouseShortDraft extends DraftBase {
    name: '住宅短租合約';
    type: 'houseShort';
    draftDetail: HouseDraftDetail;
}

export interface HouseLongDraft extends DraftBase {
    name: '住宅長租合約';
    type: 'houseLong';
    draftDetail: HouseDraftDetail;
}
```

#### 委任書
```typescript
export interface AppointDraft extends DraftBase {
    name: '委任書';
    type: 'appoint';
    draftDetail: AppointDraftDetail;
}
```

#### 商標委任書
```typescript
export interface TrademarkDraft extends DraftBase {
    name: '商標委任書';
    type: 'trademark';
    draftDetail: TrademarkDraftDetail;
}
```

#### 網站設計合約
```typescript
export interface WebsiteDraft extends DraftBase {
    name: '網站設計及保固合約';
    type: 'website';
    draftDetail: WebsiteDraftDetail;
}
```

#### 其他合約
```typescript
export interface OtherDraft extends DraftBase {
    name: '其他合約';
    type: 'other';
    draftDetail: OtherDraftDetail;
}
```

#### 聯合類型
```typescript
export type Draft = 
    | OfficeDraft 
    | AddressDraft 
    | HouseLongDraft 
    | HouseShortDraft 
    | AppointDraft 
    | OtherDraft 
    | TrademarkDraft 
    | WebsiteDraft;
```

## 🔍 型別守衛函式

套件提供了型別守衛函式，用於執行時型別檢查：

```typescript
// 檢查是否為特定草稿類型
export function isOffice(draft: DraftBase): draft is OfficeDraft;
export function isAddress(draft: DraftBase): draft is AddressDraft;
export function isHouseShort(draft: DraftBase): draft is HouseShortDraft;
export function isHouseLong(draft: DraftBase): draft is HouseLongDraft;
export function isAppoint(draft: DraftBase): draft is AppointDraft;
export function isTrademark(draft: DraftBase): draft is TrademarkDraft;
export function isWebsite(draft: DraftBase): draft is WebsiteDraft;

// 解析草稿名稱
export function ParseDraftName(type: string): string;
```

### 使用範例
```typescript
import { Draft, isOffice, isAddress } from '@flashaim-gmb/startupbase-draft/contractDraft';

function processDraft(draft: Draft) {
    if (isOffice(draft)) {
        // TypeScript 現在知道 draft 是 OfficeDraft
        console.log(draft.draftDetail.officeInfo);
    } else if (isAddress(draft)) {
        // TypeScript 現在知道 draft 是 AddressDraft
        console.log(draft.draftDetail.addressInfo);
    }
}
```

## 🚀 使用方式

### 安裝
```bash
npm install @flashaim-gmb/startupbase-draft
```

### 在前端使用 (Angular)
```typescript
// 匯入型別定義
import { Draft, DraftType, DraftBase } from '@flashaim-gmb/startupbase-draft/contractDraft';
import { DBbase } from '@flashaim-gmb/startupbase-draft';

// 在元件中使用
@Component({...})
export class DraftComponent {
    drafts: Draft[] = [];
    
    processDraft(draft: Draft) {
        // 型別安全的操作
    }
}
```

### 在後端使用 (Firebase Functions)
```typescript
// 匯入型別定義
import { Draft, isOffice } from '@flashaim-gmb/startupbase-draft/contractDraft';

// 在 Cloud Function 中使用
export const processDraft = onDocumentWritten(
    'drafts/{draftId}',
    (event) => {
        const draft = event.data?.after.data() as Draft;
        
        if (isOffice(draft)) {
            // 處理辦公室租賃合約
        }
    }
);
```

## 🔧 開發指南

### 建置專案
```bash
# 安裝依賴
npm install

# 編譯 TypeScript
npm run build

# 準備發布
npm run prepare
```

### 專案結構
```
draft/
├── 📄 index.ts              # 基礎介面匯出
├── 📄 contractDraft.ts      # 草稿相關介面
├── 📄 contractDraft.d.ts    # 型別宣告檔
├── 📄 contractDraft.js      # 編譯後的 JS
├── 📦 package.json          # 套件設定
└── 🔧 tsconfig.json         # TypeScript 設定
```

### 版本發布
```bash
# 更新版本
npm version patch|minor|major

# 發布到 NPM
npm publish

# 更新專案中的依賴
cd ../angular && npm update @flashaim-gmb/startupbase-draft
cd ../functions && npm update @flashaim-gmb/startupbase-draft
```

## 📋 最佳實踐

### 介面設計原則
1. **向後相容**: 新增欄位時使用可選屬性
2. **語義清晰**: 使用有意義的欄位名稱
3. **型別嚴格**: 避免使用 `any`，優先使用具體類型
4. **文件完整**: 為每個介面提供清楚的註解

### 版本管理
1. **語義版本**: 遵循 SemVer 規範
2. **變更日誌**: 記錄每次版本的變更內容
3. **漸進升級**: 提供平滑的升級路徑

### 測試策略
```typescript
// 型別測試範例
describe('Draft Types', () => {
    it('should validate office draft structure', () => {
        const draft: OfficeDraft = {
            type: 'office',
            name: '辦公室租賃合約',
            creator_uid: 'test-uid',
            status: '資料待填寫',
            draftDetail: {
                // ... 詳細資料
            }
        };
        
        expect(isOffice(draft)).toBe(true);
    });
});
```

## 📚 相關文件

- 📋 [專案總覽](../README.md)
- 📱 [前端開發指南](../angular/README.md)
- ⚡ [後端 API 文件](../functions/README.md)
- 📄 [TypeScript 官方文件](https://www.typescriptlang.org/)

## 🤝 貢獻指南

1. 新增介面時確保向後相容
2. 提供完整的型別守衛函式
3. 更新版本號和變更日誌
4. 測試前後端整合
5. 遵循 TypeScript 最佳實踐

---

**開發團隊**: FlashAim GMB | **語言**: TypeScript | **套件類型**: 共用介面庫