@gilbert_oliveira/commit-wizard 1.0.20 → 1.0.23

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,16 @@
1
+ #!/usr/bin/env ts-node
2
+ /**
3
+ * Realiza a chamada à API do OpenAI.
4
+ * @param prompt Texto que será enviado como mensagem do usuário.
5
+ * @param mode Define o contexto: 'commit' para gerar mensagem de commit ou outro valor para resumo.
6
+ * @returns Resposta da API (string com a mensagem ou o resumo).
7
+ */
8
+ export declare function callOpenAI(prompt: string, mode?: string): Promise<string>;
9
+ /**
10
+ * Divide o diff em chunks menores com base na contagem de tokens.
11
+ * Utiliza o gpt-tokenizer para garantir que cada chunk não exceda o limite de tokens.
12
+ * @param diff O diff completo em formato de string.
13
+ * @param maxTokens Quantidade máxima de tokens permitida para cada chunk (padrão: 1000 tokens).
14
+ * @returns Array de strings, cada uma representando um chunk.
15
+ */
16
+ export declare function chunkDiff(diff: string, maxTokens?: number): string[];
package/dist/index.js ADDED
@@ -0,0 +1,246 @@
1
+ #!/usr/bin/env ts-node
2
+ import chalk from 'chalk';
3
+ import inquirer from 'inquirer';
4
+ import os from 'os';
5
+ import path from 'path';
6
+ import fs from 'fs';
7
+ import { execSync } from 'child_process';
8
+ import ora from 'ora';
9
+ import { encode, decode } from 'gpt-tokenizer';
10
+ const OPENAI_API_KEY = process.env.OPENAI_API_KEY;
11
+ if (!OPENAI_API_KEY) {
12
+ console.log(chalk.redBright('\n🚨 Erro: A variável de ambiente ') +
13
+ chalk.yellow('OPENAI_API_KEY') +
14
+ chalk.redBright(' não está definida.\n'));
15
+ console.log(chalk.white('→ Defina sua chave com: ') +
16
+ chalk.cyan('export OPENAI_API_KEY="sua-chave"') +
17
+ chalk.white(' ou configure no seu ') +
18
+ chalk.cyan('.bashrc') +
19
+ chalk.white(' ou ') +
20
+ chalk.cyan('.zshrc\n'));
21
+ process.exit(1);
22
+ }
23
+ /**
24
+ * Realiza a chamada à API do OpenAI.
25
+ * @param prompt Texto que será enviado como mensagem do usuário.
26
+ * @param mode Define o contexto: 'commit' para gerar mensagem de commit ou outro valor para resumo.
27
+ * @returns Resposta da API (string com a mensagem ou o resumo).
28
+ */
29
+ export async function callOpenAI(prompt, mode = 'commit') {
30
+ const url = 'https://api.openai.com/v1/chat/completions';
31
+ // Escolhe o prompt inicial de acordo com o modo.
32
+ const systemPrompt = mode === 'commit'
33
+ ? "Você é um assistente que gera mensagens de commit seguindo a convenção do Conventional Commits."
34
+ : "Você é um assistente que resume alterações de código de forma breve, usando linguagem imperativa em português.";
35
+ const body = {
36
+ model: "gpt-4-turbo",
37
+ messages: [
38
+ { role: "system", content: systemPrompt },
39
+ { role: "user", content: prompt }
40
+ ],
41
+ temperature: 0.2
42
+ };
43
+ const response = await fetch(url, {
44
+ method: "POST",
45
+ headers: {
46
+ "Content-Type": "application/json",
47
+ "Authorization": `Bearer ${OPENAI_API_KEY}`
48
+ },
49
+ body: JSON.stringify(body)
50
+ });
51
+ if (!response.ok) {
52
+ throw new Error(`Erro na API OpenAI: ${response.statusText}`);
53
+ }
54
+ const data = await response.json();
55
+ // Retorna a resposta do primeiro "choice".
56
+ return data.choices[0].message.content.trim();
57
+ }
58
+ /**
59
+ * Divide o diff em chunks menores com base na contagem de tokens.
60
+ * Utiliza o gpt-tokenizer para garantir que cada chunk não exceda o limite de tokens.
61
+ * @param diff O diff completo em formato de string.
62
+ * @param maxTokens Quantidade máxima de tokens permitida para cada chunk (padrão: 1000 tokens).
63
+ * @returns Array de strings, cada uma representando um chunk.
64
+ */
65
+ export function chunkDiff(diff, maxTokens = 1000) {
66
+ // Codifica o diff para obter o array de tokens.
67
+ const tokens = encode(diff);
68
+ // Se o diff couber em um único chunk, retorna-o diretamente.
69
+ if (tokens.length <= maxTokens) {
70
+ return [diff];
71
+ }
72
+ const chunks = [];
73
+ // Percorre os tokens de forma que cada chunk contenha no máximo maxTokens tokens.
74
+ for (let i = 0; i < tokens.length; i += maxTokens) {
75
+ const chunkTokens = tokens.slice(i, i + maxTokens);
76
+ const chunkText = decode(chunkTokens);
77
+ chunks.push(chunkText);
78
+ }
79
+ return chunks;
80
+ }
81
+ // Pré-prompt para a geração da mensagem de commit conforme as convenções
82
+ const COMMIT_PROMPT = `
83
+ Por favor, escreva a mensagem de commit para este diff usando a convenção de Conventional Commits: https://www.conventionalcommits.org/en/v1.0.0/.
84
+ A mensagem deve começar com um tipo de commit, como:
85
+ feat: para novas funcionalidades
86
+ fix: para correções de bugs
87
+ chore: para alterações que não afetam a funcionalidade
88
+ docs: para mudanças na documentação
89
+ style: para alterações no estilo do código (como formatação)
90
+ refactor: para alterações no código que não alteram a funcionalidade
91
+ perf: para melhorias de desempenho
92
+ test: para alterações nos testes
93
+ ci: para mudanças no pipeline de integração contínua
94
+
95
+ Exemplo:
96
+ feat(auth): adicionar suporte ao login com Google
97
+
98
+ Caso o commit seja uma alteração significativa (breaking change), inclua um título com \`!\` após o tipo de commit e adicione a explicação em \`BREAKING CHANGE\`:
99
+ feat!(auth): reestruturar fluxo de login
100
+ BREAKING CHANGE: A API de login foi alterada e não é compatível com versões anteriores.
101
+
102
+ Gere também uma descrição mais detalhada do commit, se necessário.
103
+
104
+ Use sempre linguagem imperativa e primeira pessoa do singular, como:
105
+ - "adiciona recurso"
106
+ - "corrige bug"
107
+ - "remove arquivo"
108
+
109
+ Lembre-se: os textos fora do Conventional Commit devem ser em português.
110
+ `;
111
+ async function main() {
112
+ // Verifica se o diretório é um repositório git.
113
+ try {
114
+ execSync('git rev-parse --is-inside-work-tree', { stdio: 'ignore' });
115
+ }
116
+ catch {
117
+ console.error(chalk.red('❌ Este diretório não é um repositório git.'));
118
+ process.exit(1);
119
+ }
120
+ // Verifica se há alterações staged, desconsiderando arquivos .lock
121
+ let stagedFiles;
122
+ try {
123
+ stagedFiles = execSync('git diff --cached --name-only -- . ":(exclude)*.lock"', { encoding: 'utf8' }).toString().trim();
124
+ if (!stagedFiles) {
125
+ console.log(chalk.yellow('⚠️ Não há alterações staged para o commit.'));
126
+ process.exit(0);
127
+ }
128
+ }
129
+ catch (error) {
130
+ console.error(chalk.red('❌ Erro ao verificar alterações staged:'), error);
131
+ process.exit(1);
132
+ }
133
+ // Obtém o diff completo das alterações staged, ignorando arquivos .lock
134
+ let diff;
135
+ try {
136
+ diff = execSync('git diff --cached -- . ":(exclude)*.lock"', { encoding: 'utf8' });
137
+ }
138
+ catch (error) {
139
+ console.error(chalk.red('❌ Erro ao obter o diff:'), error);
140
+ process.exit(1);
141
+ }
142
+ // Divide o diff em chunks com base no número máximo de tokens.
143
+ const MAX_TOKENS = 1000;
144
+ const chunks = chunkDiff(diff, MAX_TOKENS);
145
+ let inputForCommit;
146
+ if (chunks.length === 1) {
147
+ inputForCommit = chunks[0];
148
+ }
149
+ else {
150
+ // Se houver vários chunks, gera um resumo para todos eles utilizando um único spinner.
151
+ const partialSummaries = [];
152
+ const chunkSummaryPrefix = "A partir do diff abaixo, extraia um resumo breve das alterações (use linguagem imperativa e em português):";
153
+ // Inicia um spinner único para todo o processo
154
+ const spinnerSummary = ora("Gerando resumo do commit.").start();
155
+ try {
156
+ for (const chunk of chunks) {
157
+ const prompt = `${chunkSummaryPrefix}\n\n${chunk}`;
158
+ const summary = await callOpenAI(prompt, 'resumo');
159
+ partialSummaries.push(summary);
160
+ }
161
+ spinnerSummary.succeed("Resumo do commit gerado.");
162
+ }
163
+ catch (error) {
164
+ spinnerSummary.fail("Erro ao gerar resumo do commit.");
165
+ console.error(chalk.red('❌ Erro ao gerar resumo para o commit:'), error);
166
+ process.exit(1);
167
+ }
168
+ inputForCommit = partialSummaries.join("\n\n");
169
+ }
170
+ // Gera a mensagem de commit com o pré-prompt e o diff (ou seus resumos).
171
+ const finalPrompt = `${COMMIT_PROMPT}\n\nDiff:\n\n${inputForCommit}`;
172
+ const spinnerCommit = ora('Gerando mensagem de commit com base no diff...').start();
173
+ let generatedMessage;
174
+ try {
175
+ generatedMessage = await callOpenAI(finalPrompt, 'commit');
176
+ // Remove os delimitadores de bloco de código (```)
177
+ generatedMessage = generatedMessage.replace(/```/g, '').trim();
178
+ spinnerCommit.succeed('Mensagem de commit gerada com sucesso.');
179
+ }
180
+ catch (error) {
181
+ spinnerCommit.fail('Erro ao gerar a mensagem de commit.');
182
+ console.error(chalk.red('❌ Erro ao gerar a mensagem de commit:'), error);
183
+ process.exit(1);
184
+ }
185
+ console.log(chalk.greenBright('\n✨ Mensagem de commit gerada automaticamente:'));
186
+ console.log(chalk.yellowBright(generatedMessage));
187
+ // Pergunta ao usuário se deseja confirmar, editar ou cancelar o commit.
188
+ const promptModule = inquirer.createPromptModule();
189
+ const { action } = await promptModule([
190
+ {
191
+ type: 'list',
192
+ name: 'action',
193
+ message: chalk.blue.bold('O que deseja fazer com a mensagem de commit gerada?'),
194
+ choices: [
195
+ { name: '📌 Confirmar e commitar', value: 'confirm' },
196
+ { name: '📝 Editar a mensagem antes de commitar', value: 'edit' },
197
+ { name: '🚫 Cancelar o commit', value: 'cancel' },
198
+ ],
199
+ },
200
+ ]);
201
+ // Cria um arquivo temporário para armazenar a mensagem (para edição se necessário).
202
+ const tempFilePath = path.join(os.tmpdir(), 'COMMIT_EDITMSG');
203
+ fs.writeFileSync(tempFilePath, generatedMessage);
204
+ if (action === 'edit') {
205
+ console.log(chalk.cyan('📝 Abrindo editor para edição da mensagem...'));
206
+ const editor = process.env.EDITOR || 'nano';
207
+ try {
208
+ execSync(`${editor} ${tempFilePath}`, { stdio: 'inherit' });
209
+ }
210
+ catch (error) {
211
+ console.error(chalk.red('❌ Erro ao abrir o editor:'), error);
212
+ process.exit(1);
213
+ }
214
+ }
215
+ else if (action === 'cancel') {
216
+ console.log(chalk.yellow('🚫 Commit cancelado pelo usuário.'));
217
+ fs.unlinkSync(tempFilePath);
218
+ process.exit(0);
219
+ }
220
+ // Lê a mensagem final (após eventual edição).
221
+ const finalMessage = fs.readFileSync(tempFilePath, 'utf8').trim();
222
+ if (!finalMessage) {
223
+ console.error(chalk.red('❌ Nenhuma mensagem inserida, commit cancelado.'));
224
+ fs.unlinkSync(tempFilePath);
225
+ process.exit(1);
226
+ }
227
+ // Captura quaisquer argumentos adicionais passados para o comando.
228
+ const gitArgs = process.argv.slice(2).join(' ');
229
+ console.log(chalk.blue('🔍 Argumentos adicionais para o commit:'), gitArgs);
230
+ // Realiza o commit com a mensagem final.
231
+ try {
232
+ execSync(`git commit -F ${tempFilePath} ${gitArgs}`, { stdio: 'inherit' });
233
+ console.log(chalk.green.bold('✅ Commit realizado com sucesso.'));
234
+ }
235
+ catch (error) {
236
+ console.error(chalk.red('❌ Erro ao realizar o commit:'), error);
237
+ }
238
+ finally {
239
+ fs.unlinkSync(tempFilePath);
240
+ }
241
+ }
242
+ main().catch((err) => {
243
+ console.error(chalk.red('❌ Erro durante o commit:'), err);
244
+ process.exit(1);
245
+ });
246
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAEA,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,QAAQ,MAAM,UAAU,CAAC;AAChC,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AACzC,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,eAAe,CAAC;AAE/C,MAAM,cAAc,GAAG,OAAO,CAAC,GAAG,CAAC,cAAc,CAAC;AAClD,IAAI,CAAC,cAAc,EAAE,CAAC;IACpB,OAAO,CAAC,GAAG,CACT,KAAK,CAAC,SAAS,CAAC,oCAAoC,CAAC;QACrD,KAAK,CAAC,MAAM,CAAC,gBAAgB,CAAC;QAC9B,KAAK,CAAC,SAAS,CAAC,uBAAuB,CAAC,CACzC,CAAC;IACF,OAAO,CAAC,GAAG,CACT,KAAK,CAAC,KAAK,CAAC,0BAA0B,CAAC;QACvC,KAAK,CAAC,IAAI,CAAC,mCAAmC,CAAC;QAC/C,KAAK,CAAC,KAAK,CAAC,uBAAuB,CAAC;QACpC,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC;QACrB,KAAK,CAAC,KAAK,CAAC,MAAM,CAAC;QACnB,KAAK,CAAC,IAAI,CAAC,UAAU,CAAC,CACvB,CAAC;IACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,UAAU,CAAC,MAAc,EAAE,OAAe,QAAQ;IACtE,MAAM,GAAG,GAAG,4CAA4C,CAAC;IAEzD,iDAAiD;IACjD,MAAM,YAAY,GAChB,IAAI,KAAK,QAAQ;QACf,CAAC,CAAC,iGAAiG;QACnG,CAAC,CAAC,gHAAgH,CAAC;IAEvH,MAAM,IAAI,GAAG;QACX,KAAK,EAAE,aAAa;QACpB,QAAQ,EAAE;YACR,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,YAAY,EAAE;YACzC,EAAE,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE;SAClC;QACD,WAAW,EAAE,GAAG;KACjB,CAAC;IAEF,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE;QAChC,MAAM,EAAE,MAAM;QACd,OAAO,EAAE;YACP,cAAc,EAAE,kBAAkB;YAClC,eAAe,EAAE,UAAU,cAAc,EAAE;SAC5C;QACD,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;KAC3B,CAAC,CAAC;IAEH,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;QACjB,MAAM,IAAI,KAAK,CAAC,uBAAuB,QAAQ,CAAC,UAAU,EAAE,CAAC,CAAC;IAChE,CAAC;IAED,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;IACnC,2CAA2C;IAC3C,OAAO,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC;AAChD,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,SAAS,CAAC,IAAY,EAAE,YAAoB,IAAI;IAC9D,gDAAgD;IAChD,MAAM,MAAM,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC;IAE5B,6DAA6D;IAC7D,IAAI,MAAM,CAAC,MAAM,IAAI,SAAS,EAAE,CAAC;QAC/B,OAAO,CAAC,IAAI,CAAC,CAAC;IAChB,CAAC;IAED,MAAM,MAAM,GAAa,EAAE,CAAC;IAE5B,kFAAkF;IAClF,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,CAAC,IAAI,SAAS,EAAE,CAAC;QAClD,MAAM,WAAW,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,GAAG,SAAS,CAAC,CAAC;QACnD,MAAM,SAAS,GAAG,MAAM,CAAC,WAAW,CAAC,CAAC;QACtC,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;IACzB,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAGD,yEAAyE;AACzE,MAAM,aAAa,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;CA4BrB,CAAC;AAEF,KAAK,UAAU,IAAI;IACjB,gDAAgD;IAChD,IAAI,CAAC;QACH,QAAQ,CAAC,qCAAqC,EAAE,EAAE,KAAK,EAAE,QAAQ,EAAE,CAAC,CAAC;IACvE,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,4CAA4C,CAAC,CAAC,CAAC;QACvE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,mEAAmE;IACnE,IAAI,WAAmB,CAAC;IACxB,IAAI,CAAC;QACH,WAAW,GAAG,QAAQ,CACpB,uDAAuD,EACvD,EAAE,QAAQ,EAAE,MAAM,EAAE,CACrB,CAAC,QAAQ,EAAE,CAAC,IAAI,EAAE,CAAC;QACpB,IAAI,CAAC,WAAW,EAAE,CAAC;YACjB,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,CAAC,4CAA4C,CAAC,CAAC,CAAC;YACxE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;IACH,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,wCAAwC,CAAC,EAAE,KAAK,CAAC,CAAC;QAC1E,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,wEAAwE;IACxE,IAAI,IAAY,CAAC;IACjB,IAAI,CAAC;QACH,IAAI,GAAG,QAAQ,CACb,2CAA2C,EAC3C,EAAE,QAAQ,EAAE,MAAM,EAAE,CACrB,CAAC;IACJ,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,yBAAyB,CAAC,EAAE,KAAK,CAAC,CAAC;QAC3D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,+DAA+D;IAC/D,MAAM,UAAU,GAAG,IAAI,CAAC;IACxB,MAAM,MAAM,GAAG,SAAS,CAAC,IAAI,EAAE,UAAU,CAAC,CAAC;IAC3C,IAAI,cAAsB,CAAC;IAE3B,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACxB,cAAc,GAAG,MAAM,CAAC,CAAC,CAAC,CAAC;IAC7B,CAAC;SAAM,CAAC;QACN,uFAAuF;QACvF,MAAM,gBAAgB,GAAa,EAAE,CAAC;QACtC,MAAM,kBAAkB,GACtB,4GAA4G,CAAC;QAE/G,+CAA+C;QAC/C,MAAM,cAAc,GAAG,GAAG,CAAC,2BAA2B,CAAC,CAAC,KAAK,EAAE,CAAC;QAEhE,IAAI,CAAC;YACH,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;gBAC3B,MAAM,MAAM,GAAG,GAAG,kBAAkB,OAAO,KAAK,EAAE,CAAC;gBACnD,MAAM,OAAO,GAAG,MAAM,UAAU,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;gBACnD,gBAAgB,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YACjC,CAAC;YACD,cAAc,CAAC,OAAO,CAAC,0BAA0B,CAAC,CAAC;QACrD,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,cAAc,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC;YACvD,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,uCAAuC,CAAC,EAAE,KAAK,CAAC,CAAC;YACzE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QACD,cAAc,GAAG,gBAAgB,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;IACjD,CAAC;IAED,yEAAyE;IACzE,MAAM,WAAW,GAAG,GAAG,aAAa,gBAAgB,cAAc,EAAE,CAAC;IACrE,MAAM,aAAa,GAAG,GAAG,CAAC,gDAAgD,CAAC,CAAC,KAAK,EAAE,CAAC;IAEpF,IAAI,gBAAwB,CAAC;IAC7B,IAAI,CAAC;QACH,gBAAgB,GAAG,MAAM,UAAU,CAAC,WAAW,EAAE,QAAQ,CAAC,CAAC;QAC3D,mDAAmD;QACnD,gBAAgB,GAAG,gBAAgB,CAAC,OAAO,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;QAC/D,aAAa,CAAC,OAAO,CAAC,wCAAwC,CAAC,CAAC;IAClE,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,aAAa,CAAC,IAAI,CAAC,qCAAqC,CAAC,CAAC;QAC1D,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,uCAAuC,CAAC,EAAE,KAAK,CAAC,CAAC;QACzE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,WAAW,CAAC,gDAAgD,CAAC,CAAC,CAAC;IACjF,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,YAAY,CAAC,gBAAgB,CAAC,CAAC,CAAC;IAElD,wEAAwE;IACxE,MAAM,YAAY,GAAG,QAAQ,CAAC,kBAAkB,EAAE,CAAC;IACnD,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,YAAY,CAA4C;QAC/E;YACE,IAAI,EAAE,MAAM;YACZ,IAAI,EAAE,QAAQ;YACd,OAAO,EAAE,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,qDAAqD,CAAC;YAC/E,OAAO,EAAE;gBACP,EAAE,IAAI,EAAE,yBAAyB,EAAE,KAAK,EAAE,SAAS,EAAE;gBACrD,EAAE,IAAI,EAAE,wCAAwC,EAAE,KAAK,EAAE,MAAM,EAAE;gBACjE,EAAE,IAAI,EAAE,sBAAsB,EAAE,KAAK,EAAE,QAAQ,EAAE;aAClD;SACF;KACF,CAAC,CAAC;IAEH,oFAAoF;IACpF,MAAM,YAAY,GAAG,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,gBAAgB,CAAC,CAAC;IAC9D,EAAE,CAAC,aAAa,CAAC,YAAY,EAAE,gBAAgB,CAAC,CAAC;IAEjD,IAAI,MAAM,KAAK,MAAM,EAAE,CAAC;QACtB,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,8CAA8C,CAAC,CAAC,CAAC;QACxE,MAAM,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,MAAM,IAAI,MAAM,CAAC;QAC5C,IAAI,CAAC;YACH,QAAQ,CAAC,GAAG,MAAM,IAAI,YAAY,EAAE,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,CAAC;QAC9D,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,2BAA2B,CAAC,EAAE,KAAK,CAAC,CAAC;YAC7D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;IACH,CAAC;SAAM,IAAI,MAAM,KAAK,QAAQ,EAAE,CAAC;QAC/B,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,CAAC,mCAAmC,CAAC,CAAC,CAAC;QAC/D,EAAE,CAAC,UAAU,CAAC,YAAY,CAAC,CAAC;QAC5B,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,8CAA8C;IAC9C,MAAM,YAAY,GAAG,EAAE,CAAC,YAAY,CAAC,YAAY,EAAE,MAAM,CAAC,CAAC,IAAI,EAAE,CAAC;IAClE,IAAI,CAAC,YAAY,EAAE,CAAC;QAClB,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,gDAAgD,CAAC,CAAC,CAAC;QAC3E,EAAE,CAAC,UAAU,CAAC,YAAY,CAAC,CAAC;QAC5B,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,mEAAmE;IACnE,MAAM,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IAChD,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,yCAAyC,CAAC,EAAE,OAAO,CAAC,CAAC;IAE5E,yCAAyC;IACzC,IAAI,CAAC;QACH,QAAQ,CAAC,iBAAiB,YAAY,IAAI,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,CAAC;QAC3E,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,KAAK,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC,CAAC;IACnE,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,8BAA8B,CAAC,EAAE,KAAK,CAAC,CAAC;IAClE,CAAC;YAAS,CAAC;QACT,EAAE,CAAC,UAAU,CAAC,YAAY,CAAC,CAAC;IAC9B,CAAC;AACH,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;IACnB,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,0BAA0B,CAAC,EAAE,GAAG,CAAC,CAAC;IAC1D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC"}
package/package.json CHANGED
@@ -1,19 +1,19 @@
1
1
  {
2
2
  "name": "@gilbert_oliveira/commit-wizard",
3
- "version": "1.0.20",
3
+ "version": "1.0.23",
4
4
  "description": "O **Commit Wizard** é uma ferramenta automatizada para geração de mensagens de commit com base na convenção de **Conventional Commits**. Ele ajuda a garantir que suas mensagens de commit sigam um padrão consistente e facilite a comunicação de mudanças no código.",
5
5
  "main": "dist/index.js",
6
6
  "type": "module",
7
7
  "bin": {
8
- "commit-wizard": "ts-node src/index.ts"
8
+ "commit-wizard": "dist/index.js"
9
9
  },
10
10
  "publishConfig": {
11
11
  "access": "public"
12
12
  },
13
13
  "scripts": {
14
- "start": "ts-node src/index.ts",
15
- "build": "tsc",
16
- "dev": "tsc --watch"
14
+ "start": "node dist/index.js",
15
+ "dev": "tsc --watch",
16
+ "build": "tsc"
17
17
  },
18
18
  "repository": {
19
19
  "type": "git",
@@ -41,10 +41,9 @@
41
41
  "homepage": "https://github.com/gilbert-oliveira/commit-wizard#readme",
42
42
  "dependencies": {
43
43
  "@types/node": "^22.14.1",
44
- "ts-node": "^10.9.2",
45
44
  "typescript": "^5.8.3",
46
45
  "gpt-tokenizer": "^1.0.0",
47
- "inquirer": "^12.5.2",
48
- "ora": "^8.2.0"
46
+ "ora": "^8.2.0",
47
+ "inquirer": "^12.5.2"
49
48
  }
50
49
  }
package/src/index.ts CHANGED
@@ -11,7 +11,20 @@ import { encode, decode } from 'gpt-tokenizer';
11
11
 
12
12
  const OPENAI_API_KEY = process.env.OPENAI_API_KEY;
13
13
  if (!OPENAI_API_KEY) {
14
- throw new Error("Chave da API do OpenAI não configurada. Defina a variável de ambiente OPENAI_API_KEY.");
14
+ console.log(
15
+ chalk.redBright('\n🚨 Erro: A variável de ambiente ') +
16
+ chalk.yellow('OPENAI_API_KEY') +
17
+ chalk.redBright(' não está definida.\n')
18
+ );
19
+ console.log(
20
+ chalk.white('→ Defina sua chave com: ') +
21
+ chalk.cyan('export OPENAI_API_KEY="sua-chave"') +
22
+ chalk.white(' ou configure no seu ') +
23
+ chalk.cyan('.bashrc') +
24
+ chalk.white(' ou ') +
25
+ chalk.cyan('.zshrc\n')
26
+ );
27
+ process.exit(1);
15
28
  }
16
29
 
17
30
  /**