diff --git a/.github/ISSUE_TEMPLATE/bug_report.yml b/.github/ISSUE_TEMPLATE/bug_report.yml
new file mode 100644
index 0000000..0d763ca
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/bug_report.yml
@@ -0,0 +1,69 @@
+name: Bug Report
+description: Create a bug report
+labels: ['bug']
+body:
+ - type: markdown
+ attributes:
+ value: |
+ Before opening a new issue:
+
+ - Do a search of existing issues.
+ - Pull the latest updates from this repository's `dev` branch.
+
+ If you need help with your own project, you can start a discussion in the [Q&A Section](https://github.com/weaponsforge/send-email/discussions/categories/q-a).
+
+ - type: textarea
+ attributes:
+ label: To Reproduce
+ description: A step-by-step description of how to reproduce the issue, or a link to the reproducible repository.
+ placeholder: |
+ 1. Start the application in development (`npm run sendemail:dev -- text -s "Title" -c "Sample body" -r a@gmail.com`)
+ 2. Press enter
+ 3. An error appears: "[ERROR] Failed to send text email: Required clientId"
+ validations:
+ required: true
+
+ - type: textarea
+ attributes:
+ label: Current vs. Expected behavior
+ description: A clear and concise description of what the bug is, and what you expected to happen.
+ placeholder: 'Following the steps from the previous section, I expected A to happen, but I observed B instead'
+ validations:
+ required: true
+
+ - type: textarea
+ attributes:
+ label: Provide environment information
+ description: Please run `npm run info` in the root directory of your project and paste the results.
+ render: bash
+ placeholder: |
+ Node version: v24.11.0
+ Platform: win32
+ Arch: x64
+ V8 version: 13.6.233.10-node.28
+ npm version: 11.6.1
+ validations:
+ required: true
+
+ - type: dropdown
+ attributes:
+ label: Which area(s) are affected? (Select all that apply)
+ multiple: true
+ options:
+ - 'Not sure'
+ - 'CLI usage'
+ - 'Authentication'
+ - 'Email templates'
+ - 'Docker image'
+ - 'Built binaries (SEA)'
+ - 'Others'
+ validations:
+ required: true
+
+ - type: textarea
+ attributes:
+ label: Additional context
+ description: |
+ Any extra information that might help us investigate.
+ placeholder: |
+ I tested my reproduction against different `googleapis` releases, and the first one that introduced the bug was "v171.4.0", since reverting to "v170.0.0" works.
diff --git a/.github/ISSUE_TEMPLATE/config.yml b/.github/ISSUE_TEMPLATE/config.yml
new file mode 100644
index 0000000..80db730
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/config.yml
@@ -0,0 +1,5 @@
+blank_issues_enabled: false
+contact_links:
+ - name: Questions?
+ url: https://github.com/weaponsforge/send-email/discussions
+ about: Ask your questions here.
diff --git a/.github/ISSUE_TEMPLATE/feature_request.yml b/.github/ISSUE_TEMPLATE/feature_request.yml
new file mode 100644
index 0000000..5aa9ac8
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/feature_request.yml
@@ -0,0 +1,36 @@
+name: Feature Request
+description: Suggest a new feature or improvement to the project
+labels: ['enhancement']
+body:
+ - type: textarea
+ attributes:
+ label: What problem will this feature address?
+ description: A clear and concise description of what the problem is.
+ placeholder: |
+ I'm always frustrated when I can't do X
+ validations:
+ required: true
+
+ - type: textarea
+ attributes:
+ label: Describe the solution you'd like
+ description: A clear and concise description of what you want to happen.
+ placeholder: Add X to the core
+ validations:
+ required: true
+
+ - type: textarea
+ attributes:
+ label: Describe alternatives you've considered
+ description: A clear and concise description of any alternative solutions or features you've considered.
+ placeholder: |
+ Maybe use Y as a workaround?
+ validations:
+ required: true
+
+ - type: textarea
+ attributes:
+ label: Additional context
+ description: Add any other context or screenshots about the feature request here.
+ validations:
+ required: false
diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md
new file mode 100644
index 0000000..cbb82f4
--- /dev/null
+++ b/.github/PULL_REQUEST_TEMPLATE.md
@@ -0,0 +1,27 @@
+## Summary
+
+
+## Related Issues
+
+
+## Type of Change
+- [ ] Bug fix
+- [ ] New feature
+- [ ] Breaking change
+- [ ] Refactor
+- [ ] Documentation
+- [ ] Other (please describe):
+
+## Checklist
+- [ ] I have read the [CONTRIBUTING.md](https://github.com/weaponsforge/send-email/blob/dev/CONTRIBUTING.md)
+- [ ] My code follows the [CODE STYLE](https://github.com/weaponsforge/send-email/blob/dev/docs/CODING_STYLE.md) of this project
+- [ ] I have added tests where applicable
+- [ ] I have tested my changes locally
+- [ ] I have linked relevant issues
+- [ ] I have added screenshots for UI changes (if applicable)
+
+## Screenshots (if applicable)
+
+
+## Additional Context
+
diff --git a/CODE_OF_CONDUCT.md b/CODE_OF_CONDUCT.md
new file mode 100644
index 0000000..a94cf98
--- /dev/null
+++ b/CODE_OF_CONDUCT.md
@@ -0,0 +1,84 @@
+
+# Contributor Covenant Code of Conduct
+
+## Our Pledge
+
+We as members, contributors, and leaders pledge to make participation in our community a harassment-free experience for everyone, regardless of age, body size, visible or invisible disability, ethnicity, sex characteristics, gender identity and expression, level of experience, education, socio-economic status, nationality, personal appearance, race, religion, or sexual identity and orientation.
+
+We pledge to act and interact in ways that contribute to an open, welcoming, diverse, inclusive, and healthy community.
+
+## Our Standards
+
+Examples of behavior that contributes to a positive environment for our community include:
+
+* Demonstrating empathy and kindness toward other people
+* Being respectful of differing opinions, viewpoints, and experiences
+* Giving and gracefully accepting constructive feedback
+* Accepting responsibility and apologizing to those affected by our mistakes, and learning from the experience
+* Focusing on what is best not just for us as individuals, but for the overall community
+
+Examples of unacceptable behavior include:
+
+* The use of sexualized language or imagery, and sexual attention or advances of any kind
+* Trolling, insulting or derogatory comments, and personal or political attacks
+* Public or private harassment
+* Publishing others' private information, such as a physical or email address, without their explicit permission
+* Other conduct which could reasonably be considered inappropriate in a professional setting
+
+## Enforcement Responsibilities
+
+Community leaders are responsible for clarifying and enforcing our standards of acceptable behavior and will take appropriate and fair corrective action in response to any behavior that they deem inappropriate, threatening, offensive, or harmful.
+
+Community leaders have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, and will communicate reasons for moderation decisions when appropriate.
+
+## Scope
+
+This Code of Conduct applies within all community spaces, and also applies when an individual is officially representing the community in public spaces. Examples of representing our community include using an official e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event.
+
+## Enforcement
+
+Instances of abusive, harassing, or otherwise unacceptable behavior may be reported to the community leaders responsible for enforcement at weaponsforge.dev@gmail.com. All complaints will be reviewed and investigated promptly and fairly.
+
+All community leaders are obligated to respect the privacy and security of the reporter of any incident.
+
+## Enforcement Guidelines
+
+Community leaders will follow these Community Impact Guidelines in determining the consequences for any action they deem in violation of this Code of Conduct:
+
+### 1. Correction
+
+**Community Impact**: Use of inappropriate language or other behavior deemed unprofessional or unwelcome in the community.
+
+**Consequence**: A private, written warning from community leaders, providing clarity around the nature of the violation and an explanation of why the behavior was inappropriate. A public apology may be requested.
+
+### 2. Warning
+
+**Community Impact**: A violation through a single incident or series of actions.
+
+**Consequence**: A warning with consequences for continued behavior. No interaction with the people involved, including unsolicited interaction with those enforcing the Code of Conduct, for a specified period of time. This includes avoiding interactions in community spaces as well as external channels like social media. Violating these terms may lead to a temporary or permanent ban.
+
+### 3. Temporary Ban
+
+**Community Impact**: A serious violation of community standards, including sustained inappropriate behavior.
+
+**Consequence**: A temporary ban from any sort of interaction or public communication with the community for a specified period of time. No public or private interaction with the people involved, including unsolicited interaction with those enforcing the Code of Conduct, is allowed during this period. Violating these terms may lead to a permanent ban.
+
+### 4. Permanent Ban
+
+**Community Impact**: Demonstrating a pattern of violation of community standards, including sustained inappropriate behavior, harassment of an individual, or aggression toward or disparagement of classes of individuals.
+
+**Consequence**: A permanent ban from any sort of public interaction within the community.
+
+## Attribution
+
+This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 2.0, available at [https://www.contributor-covenant.org/version/2/0/code_of_conduct.html][v2.0].
+
+Community Impact Guidelines were inspired by [Mozilla's code of conduct enforcement ladder][Mozilla CoC].
+
+For answers to common questions about this code of conduct, see the FAQ at [https://www.contributor-covenant.org/faq][FAQ]. Translations are available at [https://www.contributor-covenant.org/translations][translations].
+
+[homepage]: https://www.contributor-covenant.org
+[v2.0]: https://www.contributor-covenant.org/version/2/0/code_of_conduct.html
+[Mozilla CoC]: https://github.com/mozilla/diversity
+[FAQ]: https://www.contributor-covenant.org/faq
+[translations]: https://www.contributor-covenant.org/translations
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
new file mode 100644
index 0000000..9f49dbe
--- /dev/null
+++ b/CONTRIBUTING.md
@@ -0,0 +1,67 @@
+# Contribution Guidelines
+
+Welcome to theΒ **send-email**Β repository! We're excited to have you contribute to sending text and HTML-format emails more accessible via command line interface (CLI). To ensure a smooth contribution process for everyone, please follow these guidelines.
+
+## Getting Started
+
+1. **Fork the Repository:** Start by forking the repository's `"dev"` branch to your GitHub account. This creates your own copy of the project where you can make changes.
+
+2. **Clone Your Fork:** Clone your forked repository to your local machine using Git. This allows you to work on the files locally.
+ ```sh
+ git clone https://github.com/yourusername/send-email.git
+ ```
+
+3. **Set Upstream Remote:** Add the original repository as an upstream remote to your local clone. This helps you to keep your fork up to date.
+ ```sh
+ git remote add upstream https://github.com/weaponsforge/send-email.git
+ ```
+
+## Making Changes
+
+1. **Create a New Branch:** Always work on a new branch for your changes. This keeps your contributions organized and separate from the main branch.
+ ```sh
+ git checkout -b feat/your-new-feature-name
+ ```
+
+2. **Add Your Content:** Make your changes or additions to the project. If you're adding new content, ensure it's placed in the correct directory and follows intuitive naming conventions and TypeScript coding best practices and patterns described in the [CODING STYLE](/docs/CODING_STYLE.md).
+
+ > Before commiting your changes, format your code with `"npm run lint:fix"`, and ensure all updates pass the `"npm run lint"`, `"npm run transpile:noemit"` and `"npm test"` scripts.
+
+3. **Commit Your Changes:** After making your changes, commit them to your branch. Use clear and concise commit messages to describe your updates.
+ ```sh
+ git add .
+ git commit -m "Add a brief description of your changes"
+ ```
+
+4. **Keep Your Fork Updated:** Regularly sync your fork's `"dev"` branch with the upstream repository to keep it up to date. This reduces potential merge conflicts.
+ ```sh
+ git fetch upstream
+ git checkout dev
+ git merge upstream/dev
+ git push origin dev
+ ```
+
+## Submitting Contributions
+
+1. **Push Your Changes:** Push your changes to your fork on GitHub.
+ ```sh
+ git push origin feat/your-new-feature-name
+ ```
+
+2. **Create a Pull Request (PR):** Go to the original **send-email** repository on GitHub and create a new pull request. Base your PR on your feature branch and target the `"dev"` branch of the upstream repository.
+
+3. **Describe Your Contribution:** Provide a clear and detailed description of your pull request. Include the purpose of your changes and any other relevant information.
+
+4. **Review and Collaboration:** Once your PR is submitted, the project maintainers will review your contributions. Be open to feedback and be ready to make additional changes if requested.
+
+## Guidelines
+
+1. **Quality:** Ensure your contributions are high quality, with no spelling or grammatical errors.
+
+2. **Relevance:** Content should be relevant to mostly Node.js and TypeScript - coding structure, patterns, naming conventions, optimizations, directory/folder colocation structures and conventions, and/or usage of notable Node libraries for Node.js CLI development closely following and improving this repository's [CODING STYLE](/docs/CODING_STYLE.md).
+
+3. **Working functionality:** For pull requests involving new features or major updates, ensure the changes are fully functional and optimized. Aim to keep PRs within **`~700` lines of code changes**, breaking them into smaller, self-contained parts when possible. PRs exceeding **`~1000+` lines** may be accepted when justified (e.g., major refactors or foundational features).
+
+4. **Respect:** Respect the structure and formatting of the existing project. Follow the standard ESLint rules defined in its `app/eslint.config.mjs` file.
+
+Thank you for contributing to the **send-email** repository. Your efforts help in sending emails more accessible for everyone.
diff --git a/README.md b/README.md
index 6e27126..407d6a5 100644
--- a/README.md
+++ b/README.md
@@ -11,7 +11,7 @@ NPM library and CLI for sending text and HTML emails using Gmail SMTP with Googl
> A Node.js package is available at https://www.npmjs.com/package/@weaponsforge/sendemail
>
> - **Pre-compiled Windows binaries**
-> Pre-compiled [Windows binaries](#οΈ-building-the-windows-executable-file) are available for download in the latest [Releases](https://github.com/weaponsforge/sendemail/releases) download page.
+> Pre-compiled [Windows binaries](#οΈ-building-the-windows-executable-file) are available for download in the latest [Releases](https://github.com/weaponsforge/send-email/releases) download page.
>
> - **Docker image**
> A Docker image is available at https://hub.docker.com/r/weaponsforge/sendemail
@@ -56,10 +56,16 @@ NPM library and CLI for sending text and HTML emails using Gmail SMTP with Googl
5. [vitest](https://www.npmjs.com/package/vitest) `v4.0.18` - Runs tests
6. [commander](https://www.npmjs.com/package/commander) `v14.0.3` - CLI library
7. [sanitize-html](https://www.npmjs.com/package/sanitize-html) `v2.17.1` - Sanitizes WYSIWYG HTML input
+8. [zod](https://www.npmjs.com/package/zod) `v3.24.2` - Run-time input validation
+9. [ejs](https://www.npmjs.com/package/ejs) `v4.0.1` - Composes HTML with dynamic text content
+## Contributing
+
+We welcome contributions! Please see [CONTRIBUTING.md](/CONTRIBUTING.md) and the [CODING STYLE](/docs/CODING_STYLE.md) for guidelines.
+
## π Quickstart
1. Create a `.env` file in the `/app` directory, replacing the contents of the `.env.example` file with actual values.
@@ -292,6 +298,10 @@ Copies the EJS email template into the `/dist/templates` directory.
This script runs automatically after `"npm run transpile"`, copying the `"/app/src/templates/email.ejs"` to the `"/dist/templates"` directory.
+### `npm run info`
+
+Logs the installed Node.js and npm version, environment platform, architecture and V8 version.
+
### C. CLI π»
### `npm start`
diff --git a/SECURITY.md b/SECURITY.md
new file mode 100644
index 0000000..80599d2
--- /dev/null
+++ b/SECURITY.md
@@ -0,0 +1,23 @@
+## Reporting Security Issues
+
+**Please do not report security vulnerabilities through public GitHub issues.**
+
+If you believe you have found a security vulnerability, we encourage you to let the Maintainer know right away.
+
+They will investigate all legitimate reports and do our best to quickly fix the problem.
+
+Email `weaponsforge.dev@gmail.com` to disclose any security vulnerabilities.
+
+You should receive a response within 3 business days. If for some reason you do not, please follow up via email to ensure they received your original message.
+
+Please include the requested information listed below (as much as you can provide) to help us better understand the nature and scope of the possible issue:
+
+- Type of issue (e.g. leaked secrets, malware installation, CVE, cross-site scripting, etc.)
+- Full paths of source file(s) related to the manifestation of the issue
+- The location of the affected source code (tag/branch/commit or direct URL)
+- Any special configuration required to reproduce the issue
+- Step-by-step instructions to reproduce the issue
+- Proof-of-concept or exploit code (if possible)
+- Impact of the issue, including how an attacker might exploit the issue
+
+This information will help the Maintainer triage your report more quickly.
diff --git a/app/package-lock.json b/app/package-lock.json
index 832eddc..eb52cf2 100644
--- a/app/package-lock.json
+++ b/app/package-lock.json
@@ -1,12 +1,12 @@
{
"name": "@weaponsforge/sendemail",
- "version": "1.2.3",
+ "version": "1.2.4",
"lockfileVersion": 3,
"requires": true,
"packages": {
"": {
"name": "@weaponsforge/sendemail",
- "version": "1.2.3",
+ "version": "1.2.4",
"license": "MIT",
"dependencies": {
"commander": "^14.0.3",
diff --git a/app/package.json b/app/package.json
index 15d4622..526a714 100644
--- a/app/package.json
+++ b/app/package.json
@@ -1,6 +1,6 @@
{
"name": "@weaponsforge/sendemail",
- "version": "1.2.3",
+ "version": "1.2.4",
"description": "Sends emails using Gmail SMTP with username/pw or Google OAuth2",
"main": "dist/index.js",
"types": "./dist/index.d.ts",
@@ -43,7 +43,8 @@
"docker:watch:win": "tsc -p tsconfig.json --watch --watchFile dynamicPriorityPolling --watchDirectory dynamicPriorityPolling",
"docker:test:ui:win": "export CHOKIDAR_USEPOLLING=1 && export CHOKIDAR_INTERVAL=1000 && npm run docker:test:ui",
"sendemail": "node ./dist/scripts/cli/send.js",
- "sendemail:dev": "tsx ./src/scripts/cli/send.ts"
+ "sendemail:dev": "tsx ./src/scripts/cli/send.ts",
+ "info": "tsx ./src/scripts/envinfo.ts"
},
"repository": {
"type": "git",
diff --git a/app/sea-config.json b/app/sea-config.json
index 0e549e8..0c73e30 100644
--- a/app/sea-config.json
+++ b/app/sea-config.json
@@ -2,6 +2,7 @@
"main": "build/sendemail.cjs",
"output": "build/sea-prep.blob",
"format": "module",
+ "execArgv": ["--no-warnings"],
"disableExperimentalSEAWarning": true,
"useCodeCache": false,
"useSnapshot": false
diff --git a/app/src/scripts/cli/send.ts b/app/src/scripts/cli/send.ts
index 0dbd637..576d665 100644
--- a/app/src/scripts/cli/send.ts
+++ b/app/src/scripts/cli/send.ts
@@ -77,8 +77,8 @@ program.command(CLI_META.CMD_SEND_HTML.NAME)
/**
* Usage:
- * - npm run send-cli:dev -- text [options]
- * - npm run send-cli:dev -- html [options]
+ * - npm run sendemail:dev -- text [options]
+ * - npm run sendemail:dev -- html [options]
* - npx tsx src\scripts\cli\send.ts help text
* - npx tsx src\scripts\cli\send.ts help html
*/
diff --git a/app/src/scripts/envinfo.ts b/app/src/scripts/envinfo.ts
new file mode 100644
index 0000000..8327b88
--- /dev/null
+++ b/app/src/scripts/envinfo.ts
@@ -0,0 +1,16 @@
+import { execSync } from "child_process"
+
+const main = () => {
+ console.log('Node version:', process.version)
+ console.log('Platform:', process.platform)
+ console.log('Arch:', process.arch)
+ console.log('V8 version:', process.versions.v8)
+
+ try {
+ console.log('npm version:', execSync('npm -v').toString().trim())
+ } catch {
+ console.log('npm version: unavailable')
+ }
+}
+
+main()
diff --git a/app/src/utils/helpers.ts b/app/src/utils/helpers.ts
index dff56ff..261615f 100644
--- a/app/src/utils/helpers.ts
+++ b/app/src/utils/helpers.ts
@@ -1,10 +1,8 @@
import { promises as fs } from 'node:fs'
import path, { dirname } from 'node:path'
-import sea from 'node:sea'
import { fileURLToPath } from 'url'
import dotenv from 'dotenv'
-const isSea = sea.isSea()
/**
* Creates a sequence of N-length `"a"` characters
@@ -87,9 +85,4 @@ export const loadEnv = (pathToEnv: string | undefined) => {
path: pathToEnv,
quiet: true
})
-
- if (isSea) {
- // Disable Node deprecation warnings in the CLI build output
- process.noDeprecation = true
- }
}
diff --git a/docs/CODING_STYLE.md b/docs/CODING_STYLE.md
new file mode 100644
index 0000000..2ac9520
--- /dev/null
+++ b/docs/CODING_STYLE.md
@@ -0,0 +1,167 @@
+## Coding Style
+
+This document outlines the general TypeScript and CLI/library coding styles and guidelines for this repository.
+
+### Table of Contents
+
+- [Project Folder Structure](#-project-folder-structure)
+- [Coding Practices and Guidelines](#-coding-practices-and-guidelines)
+ - [General Coding Guidelines](#-general-coding-guidelines)
+ - [Library Code](#-library-code)
+ - [Code Documentation](#-code-documentation)
+ - [Linting and Formatting](#-linting-and-formatting)
+ - [Use of External Libraries](#-use-of-external-libraries)
+ - [Testing](#-testing)
+
+## π Project Folder Structure
+
+It follows the directory structure within the `/app` directory:
+
+> [!NOTE]
+> π build
+> π dist
+> π html
+> π scripts
+> π src
+> ββ π \_\_tests\_\_
+> ββ π demo
+> ββ π scripts
+> ββ π types
+> ββ π utils
+> ββ π index.ts
+> ββ π .env.example
+> ββ π .gitignore
+> ββ π .dockerignore
+> ββ π Dockerfile
+> ββ π package.json
+> ββ π package-lock.json
+> ββ π sea-config.json
+> ββ π eslint.config.mjs
+> ββ π vite.config.ts
+> ββ π tsconfig.json
+> ββ π ...
+> π README.md
+
+### Main Folders and Content
+
+**What you should (and shouldn't) edit**
+
+β
**Edit:**
+- `src/**` (main TypeScript source)
+- Top-level build scripts in `scripts/**` (bash / automation)
+
+ποΈπ« **Auto-generated (do not edit):**
+- `dist/**` (TS build output; local, published to NPM)
+- `build/**` (SEA build output; local, published to GitHub Releases)
+- `html/**` (test coverage output; local)
+
+#### π build
+
+Generated SEA artifacts (Windows EXE + blob output with `build-sea-win.sh`). Local build output only. This is what gets published to the GitHub Releases page.
+Do not edit manually.
+
+#### π dist
+
+Generated output from TypeScript build (JS + .d.ts + sourcemaps). This is what gets published to the npm registry.
+Do not edit manually.
+
+#### π html
+
+Generated Vitest coverage website output.
+Do not edit manually.
+
+#### π scripts
+
+Contains Build automation scripts (bash)
+
+#### π src
+
+Contains the main source, configurations, and utilities used throughout the app.
+
+- `/__tests__` β Vitest test files used for testing critical library and CLI features.
+- `/demo` β Sample codes demonstrating library usage.
+- `/scripts` β CLI source code (TypeScript).
+- `/types` β Main TypeScript interfaces, types and constructs used within the app.
+- `/utils` β General-purpose utility functions, such as string formatters, directory path conventions and constant configurations.
+
+#### π src/lib
+
+Contains the main application source codes, classes and logic.
+
+- `/email` β Classes and scripts for handling email transport and content formatting and transformation.
+- `/google` β Class that manages and validates input for the Google OAuth2.
+- `/validator` β A wrapper around the `zod` Schemas containing generic log output formatters and utilities.
+
+#### π src/lib/utils/templates
+
+This folder contains the [EJS](https://github.com/mde/ejs) HTML template used in sending emails, and other template formats for various use cases.
+
+## π Coding Practices and Guidelines
+
+### π General Coding Guidelines
+
+- Use **`LF` (Line Feed)** as the line ending format for all code and other files to ensure consistency across environments and platforms.
+- Use **arrow functions** instead of traditional function declarations when defining functions and methods. Only use `function()` definitions for specific cases.
+- Follow **camelCase** for naming variables, files, functions/methods and non-component folders.
+- Follow **PascalCase** for naming **Zod** schemas, TypeScript `types`, `interfaces`, `enums` and other TypeScript constructs.
+- Follow consistent file naming conventions based on content:
+ - Use `*.schema.ts` for files containing Zod schemas.
+ - Use `*.enum.ts` for files containing only enums.
+ - Use `*.interface.ts` for files containing only interfaces.
+ - Use `*.types.ts` for files that include a mix of types, interfaces, enums, or other related constructs.
+- Always define the **types** of function parameters and return values. Use TypeScript **interfaces** or **types** for generic parameters when applicable.
+ - Avoid `any` unless absolutely necessary (prefer `unknown`, `Record`, etc.)
+- Aim to keep each source fileβ**under approximately 250 lines of code**. If a file exceeds this size, **consider refactoring** it into smaller, more focused files to improve clarity and maintainability.
+- Use **early `return` statements** to exit hooks or functions as soon as possible when conditions aren't met, to avoid unnecessary processing and to keep the logic clean and efficient.
+- Store constant values (e.g., strings or numbers) in **well-named variables** to improve readability and maintainability.
+ ```typescript
+ β
const PROGRAM_NAME = 'my-app'
+ program.name(PROGRAM_NAME)
+ β program.name('my-app')
+ ```
+
+### π» Library Code
+
+- Implement CLI features within the `π src/scripts` directory.
+- Think in OOP and use `classes` to define app-wide logic in the `π src/lib` directory whenever possible.
+- Export new library scripts or classes in the `/src/index.ts` file.
+
+### π Code Documentation
+
+- Use **JSDoc-style comments** to describe function parameters, return types, and TypeScript type or interface definitions.
+- Add **minimal but meaningful inline comments** where necessary to clarify intent, especially for complex or non-obvious logic.
+- Use **descriptive and self-explanatory variable names** to reduce the need for excessive comments and improve overall code readability.
+
+### π§Ή Linting and Formatting
+
+- Linting is handled by **ESLint**, configured via `eslint.config.mjs`.
+- All code should pass `"npm run lint"` and `"npm run transpile:noemit"` before commit.
+
+### π¦ Use of External Libraries
+
+- Strive to **minimize external dependencies**, especially for simple or easily implementable functionality (e.g., a function that sums two numbers).
+- Only use third-party Node libraries when **truly necessary**βfor example, when a library:
+ - Provides functionality that would be complex or time-consuming to build from scratch
+ - Is used frequently across the app
+ - Helps avoid "reinventing the wheel" for heavy processing tasks
+- Before adding a library, consider the following π’ green flags:
+ - It comes from a **credible author or organization**, with an active and trustworthy GitHub repository
+ - It has **high usage** and community trust (e.g., ~100K+ downloads on the NPM registry)
+ - It has **small and lightweight footprint** (eg., about ~300KB-2MB unpacked) or if it supports **tree-shaking**.
+ - The source code is **open, transparent, and actively maintained** (eg., few open GitHub Issues or PRs)
+ - Even if not actively maintained, the library still **aligns with your needs** and is simple enough to extend or adapt for custom use (e.g., a JavaScript `class` that can be easily refactored or subclassed (`extend`) for custom use)
+
+### π§ͺ Testing
+
+> [!NOTE]
+> _This app uses **Vitest** for testing feature-level processes._
+
+- Create and run tests for critical feature-level components, classes, or scripts.
+- Place test files in the `/src/__tests__` directory.
+- Name test files to match the target module, using the suffix: `*.test.ts`.
+ > **Example:** `send.ts` β `send.test.ts`
+- **Selectively write tests** for critical or global, features, or business logic as needed.
+- All code should pass `"npm test"` before commit.
+
+@weaponsforge
+20260226
diff --git a/docs/README_NPM.md b/docs/README_NPM.md
index a287b80..7451e34 100644
--- a/docs/README_NPM.md
+++ b/docs/README_NPM.md
@@ -49,6 +49,10 @@ NPM library for sending text and HTML emails using Gmail SMTP with Google OAuth2
+## Contributing
+
+We welcome contributions! Please see [CONTRIBUTING.md](/CONTRIBUTING.md) and the [CODING STYLE](/docs/CODING_STYLE.md) for guidelines.
+
## π Quickstart
1. Install the library.