# Huong dan phat trien

## Yeu cau he thong

- **Node.js** >= 20
- **npm** >= 8
- **Chrome 88+** hoac **Firefox 78+** de test

## Cai dat

```bash
git clone <repo-url>
cd AutoShopee-Kit

npm install --legacy-peer-deps
```

> `--legacy-peer-deps` can thiet do conflict giua eslint versions.

Sau khi install, `postinstall` tu dong chay `wxt prepare` de generate types vao `.wxt/`.

---

## Build System

Project dung **WXT** (Vite-based) de build browser extension.

- Config chinh: `wxt.config.ts`
- Entrypoints: `entrypoints/`
- Output: `dist/`

### Cac lenh

#### Development

```bash
# Dev mode voi HMR (Chrome, tu dong mo browser)
npm run dev

# Dev mode cho Firefox
npm run dev:firefox

# Mo Vue DevTools (remote debugging)
npm run dev:tool
```

`npm run dev` se:
1. Start Vite dev server (HMR cho popup/options)
2. Build tat ca entrypoints
3. Tu dong mo Chrome voi extension loaded
4. Watch file changes — auto-reload content scripts va background

#### Production Build

```bash
# Build Chrome (Manifest V3)
npm run build:chrome

# Build Firefox (Manifest V2 — tu dong)
npm run build:firefox
```

#### Packaging

```bash
# Build + tao ZIP cho Chrome Web Store
npm run zip:chrome

# Build + tao ZIP cho Firefox Add-ons
npm run zip:firefox

# Upload ZIP len S3
npm run zip:s3
```

#### Code Quality

```bash
npm run lint          # ESLint check
npm run lint:fix      # ESLint autofix
npm run format        # Prettier + ESLint fix
npm run pretty        # Prettier only
```

---

## Cau truc entrypoints

WXT dung file-based entrypoints. Moi file trong `entrypoints/` tu dong duoc WXT phat hien va build.

```
entrypoints/
  popup/
    index.html              ← HTML template
    main.js                 ← Vue app entry
  options/
    index.html
    main.js
  background.js             ← Service worker (Chrome) / background script (Firefox)
  *.content.js              ← Content scripts (ten file ket thuc bang .content.js)
```

### Quy tac dat ten content script

| File | Inject vao |
|---|---|
| `all-ping.content.js` | `<all_urls>` |
| `shopee-client.content.js` | `https://shopee.vn/*` |
| `shopee-seller.content.js` | `https://banhang.shopee.vn/*` |
| `shopee-seller-order.content.js` | `https://banhang.shopee.vn/portal/sale/order/*` |
| `shopee-fetch.content.js` | Shopee (world: MAIN) |
| `lazada.content.js` | `https://*.lazada.*/*` |
| `tiki.content.js` | `https://*.tiki.vn/*` |
| `tiktok.content.js` | `https://*.tiktok.com/*` |

### Cau truc content script

Moi content script entrypoint la wrapper goi `defineContentScript()`:

```js
// entrypoints/shopee-seller-order.content.js
export default defineContentScript({
  matches: ['https://banhang.shopee.vn/portal/sale/order/*'],
  main() {
    import('@content/shopee/seller/order/index.js');
  },
});
```

- `matches` — URL patterns de inject
- `runAt` — `document_idle` (default), `document_start`, `document_end`
- `world` — `ISOLATED` (default) hoac `MAIN` (truy cap DOM cua trang)
- `main()` — dynamic `import()` load logic goc tu `src/content/`

### Background script

```js
// entrypoints/background.js
export default defineBackground(() => {
  import('@background/index.js');
});
```

WXT tu dong xu ly:
- Chrome: `service_worker` (MV3)
- Firefox: `background.scripts` (MV2)

---

## Them feature moi

### Them content script moi

1. Tao logic trong `src/content/`:

```js
// src/content/shopee/seller/newFeature/index.js
import { onChangeTab } from '@content/service/util';

const init = () => {
  // Logic
};

document.addEventListener('readystatechange', init);
onChangeTab(init);
```

2. Tao entrypoint wrapper:

```js
// entrypoints/shopee-seller-new-feature.content.js
export default defineContentScript({
  matches: ['https://banhang.shopee.vn/portal/new-feature*'],
  main() {
    import('@content/shopee/seller/newFeature/index.js');
  },
});
```

Done. WXT tu dong phat hien file moi va build. Khong can sua config nao khac.

### Them permission moi

Sua `wxt.config.ts` → `manifest` → `permissions` hoac `host_permissions`:

```ts
permissions: ['storage', 'tabs', 'alarms', 'webRequest', 'notifications', 'cookies', 'newPermission'],
```

### Them web accessible resource

Sua `wxt.config.ts` → `manifest` → `web_accessible_resources`:

```ts
web_accessible_resources: [
  {
    resources: ['pdfjs/*', 'new-resource.js'],
    matches: ['*://*/*'],
  },
],
```

Hoac dat file vao `public/` — WXT tu dong include.

---

## Path Aliases

| Alias | Map den | Ghi chu |
|---|---|---|
| `@` | `src/app/` | WXT built-in (tu `srcDir`) |
| `~` | `src/app/` | WXT built-in (giong `@`) |
| `@@` | project root | WXT built-in |
| `~~` | project root | WXT built-in |
| `@content` | `src/content/` | Custom alias |
| `@background` | `src/background/` | Custom alias |
| `@type` | `src/app/types/` | Custom alias |

Su dung:

```js
import { apiUrl } from '@/config/env';           // src/app/config/env.js
import { loggerContent } from '@/plugins/logger'; // src/app/plugins/logger
import { onChangeTab } from '@content/service/util'; // src/content/service/util
```

> **Luu y**: Khong the override alias `@` trong `wxt.config.ts` vi WXT luon gan `@` = `srcDir`. De thay doi, sua `srcDir` trong config.

---

## Bien moi truong

### File `.env`

```env
VITE_APP_NAME=AutoShopee Kit
VITE_API_URL=https://autoshopee.com
VITE_CMS_URL=https://content.autoshopee.com
VITE_IMAGE_HANDLER_URL=https://chinhanh.pro
VITE_SOCKET_URL=https://ws.autoshopee.com
VITE_WORKER_URL=https://worker-shopee-api.autoshopee.com
VITE_WORKER_SOCKET=https://worker-shopee-ws.autoshopee.com
```

### Quy tac

- Tat ca bien phai co prefix `VITE_` de expose sang client code
- Truy cap bang `import.meta.env.VITE_*`
- File env: `.env` (chung), `.env.development`, `.env.production`

### Bien co san (WXT/Vite)

| Bien | Gia tri |
|---|---|
| `import.meta.env.MODE` | `'development'` / `'production'` |
| `import.meta.env.DEV` | `true` / `false` |
| `import.meta.env.PROD` | `true` / `false` |
| `import.meta.env.BROWSER` | `'chrome'` / `'firefox'` |
| `import.meta.env.MANIFEST_VERSION` | `2` / `3` |
| `import.meta.env.CHROME` | `true` neu build Chrome |
| `import.meta.env.FIREFOX` | `true` neu build Firefox |

### Su dung trong code

```js
// src/app/config/env.js — trung tam, tat ca file khac import tu day
export const hostUrl = import.meta.env.VITE_API_URL;
export const isDevMode = import.meta.env.DEV;
export const isProductionMode = import.meta.env.PROD;
```

---

## Manifest

Manifest duoc cau hinh trong `wxt.config.ts` thay vi file JSON rieng:

```ts
manifest: ({ browser, mode }) => {
  const isDevMode = mode === 'development';
  return {
    name: isDevMode ? 'AutoShopee Kit Dev' : 'AutoShopee Kit',
    permissions: ['storage', 'tabs', ...],
    host_permissions: [...],
    // browser-specific
    ...(browser === 'chrome' ? { incognito: 'split' } : {}),
    ...(browser === 'firefox' ? { browser_specific_settings: { gecko: { id: '...' } } } : {}),
  };
},
```

WXT tu dong:
- Chuyen MV3 → MV2 cho Firefox
- Chuyen `service_worker` → `background.scripts` cho Firefox
- Generate `content_scripts` tu cac file `*.content.js`
- Merge `web_accessible_resources`

---

## Cai extension vao trinh duyet

### Chrome (Development)

```bash
npm run dev
```

WXT tu dong mo Chrome voi extension loaded. Neu can load thu cong:

1. Mo `chrome://extensions/`
2. Bat **Developer mode**
3. Click **Load unpacked**
4. Chon `dist/chrome-mv3-dev/`

### Firefox (Development)

```bash
npm run dev:firefox
```

Hoac load thu cong:

1. Mo `about:debugging#/runtime/this-firefox`
2. Click **Load Temporary Add-on**
3. Chon `dist/firefox-mv2-dev/manifest.json`

### Production

1. `npm run build:chrome` hoac `npm run build:firefox`
2. Load tu `dist/chrome-mv3/` hoac `dist/firefox-mv2/`

---

## HMR & Hot Reload

| Thanh phan | Hanh vi khi thay doi file |
|---|---|
| Popup page | HMR — cap nhat khong reload |
| Options page | HMR — cap nhat khong reload |
| Content scripts | Auto-reload — extension reload |
| Background | Auto-reload — service worker restart |

### Keyboard shortcut trong dev

- `o + Enter` — mo lai browser
- `Alt+R` — reload extension

---

## Quy uoc code

1. **Vue Components**: Chi dung Options API (KHONG Composition API)
2. **Types**: JSDoc trong `src/app/types/`, KHONG inline
3. **Linting**: ESLint Airbnb base
4. **Formatting**: Prettier (auto qua Husky pre-commit)
5. **Console**: Khong dung `console.log` — dung logger system
6. **Import**: Dung path aliases (`@`, `@content`, `@background`)
7. **Module**: ESM only (`import`/`export`), KHONG dung `require()`

---

## Logging

He thong logger tuy chinh thay the `console.log`:

```js
import { loggerContent } from '@/plugins/logger';

loggerContent.log({ msg: 'MESSAGE_ID', data });
loggerContent.error({ msg: 'ERROR_ID', error });
```

- Phan loai: shopee, worker, api, vue, content, background
- Color-coded output
- Silent mode trong production (dieu khien qua `isShowLogger`)

---

## Troubleshooting

### Extension khong load duoc
- Kiem tra `dist/` da build chua
- Kiem tra manifest.json khong loi syntax: `cat dist/chrome-mv3-dev/manifest.json`
- Xem Console trong background page (chrome://extensions → Inspect views)

### HMR khong hoat dong
- Kiem tra dev server chay: `http://localhost:3001`
- Thu reload: nhan `o + Enter` trong terminal
- Restart: `Ctrl+C` roi `npm run dev` lai

### Content script khong inject
- Kiem tra URL pattern trong `defineContentScript({ matches: [...] })`
- Kiem tra permission `host_permissions` trong `wxt.config.ts`
- Mo DevTools tren trang target → Console → kiem tra script loaded

### Build loi
- Xoa cache: `rm -rf .wxt/ dist/ node_modules/.vite/`
- Chay lai: `npx wxt prepare && npm run dev`

### PouchDB sync loi
- Kiem tra ket noi internet
- Kiem tra credentials
- Xem logs tu `pouchdb-debug` plugin (dev mode)

---

## CI/CD

File `.drone.yml` — trigger khi push len branch `dev`:

1. Install dependencies
2. Build + zip Chrome
3. Build + zip Firefox
4. Upload artifacts len S3

WXT `zip` command tu dong build + tao zip trong 1 lenh.
