bddgenx 2.3.1 → 2.3.3

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 3f6fc74668686947a758772af02a322b5b4cc80ca6f992ac79f53c256746fc60
4
- data.tar.gz: 331ec1c98945e65bf99081662f7393789922381a9ae684fa5aa256e8a7aa6c11
3
+ metadata.gz: b5f895b922c947b8d97296d56a17cfbdc9c31e5bbf6bbfc383c01ebc3e4cfe9d
4
+ data.tar.gz: 001d68f9b89e12e52e446bc02db6ee249392c864ad1955172dff31203a1a6a6c
5
5
  SHA512:
6
- metadata.gz: d37b9a635ee34de1f39eab561f48f714423907b30e01531c46af5e5805d6357190d4a5f100c1e4bd8231c79086383fd54487d190c25893df8290c911b6492c5a
7
- data.tar.gz: c315c467125e9b4cd9c72cd4c7f72aee8b39430e4209f4ef1117802209bbb25fcd50aa8b96de3bf903719697d6bf0758e92a2fdb8f959d417e493d01ac6efe94
6
+ metadata.gz: ce291e292b64946fcc493e9a590ef335fc652d321bee8637fdd7b5c30a7d411f34d7a26baf26c2a8f6ea1208fb2c943c11219b07695aa6e87fd7a932677a25a3
7
+ data.tar.gz: 52710f0f98ba329340956d8e657c09fd802f7f51a34b6437fd692f1e20924db8354a0ed3adcaa29d297461bf566e31fd9dfff54efa9945bbbd719f3f619c4c57
data/README.md CHANGED
@@ -147,22 +147,82 @@ Bddgenx::Runner.execute
147
147
 
148
148
  ---
149
149
 
150
+ ## 📦 Geração manual via Rake
151
+ ```Ruby
152
+ require 'rake'
153
+ require 'bddgenx'
154
+
155
+ namespace :bddgenx do
156
+ desc 'Executa geração interativa: escolha entre static, chatgpt, gemini ou deepseek'
157
+ task :generate do
158
+ puts "=== Qual modo deseja usar para gerar os cenários? ==="
159
+ puts "1. static (sem IA)"
160
+ puts "2. chatgpt (via OpenAI)"
161
+ puts "3. gemini (via Google)"
162
+ print "Digite o número (1-3): "
163
+
164
+ escolha = STDIN.gets.chomp.to_i
165
+
166
+ modo = case escolha
167
+ when 1 then :static
168
+ when 2 then :chatgpt
169
+ when 3 then :gemini
170
+ else
171
+ puts "❌ Opção inválida. Saindo."; exit 1
172
+ end
173
+
174
+ Bddgenx.configure do |config|
175
+ config.mode = modo
176
+ config.openai_api_key_env = 'OPENAI_API_KEY'
177
+ config.gemini_api_key_env = 'GEMINI_API_KEY'
178
+ end
179
+
180
+ # ⚠️ Limpa o ARGV antes de executar para evitar que [static] seja interpretado como nome de arquivo
181
+ ARGV.clear
182
+
183
+ ENV['BDDGENX_MODE'] = modo.to_s
184
+ puts "\n⚙️ Modo selecionado: #{modo}\n\n"
185
+ Bddgenx::Runner.execute
186
+ end
187
+ end
188
+ ```
189
+
150
190
  ## 📝 Formato do Arquivo de Entrada (`.txt`)
151
191
 
152
192
  ```txt
153
193
  # language: pt
154
194
  Como um usuário do sistema
155
- Quero fazer login
156
- Para acessar minha conta
195
+ Quero fazer login corretamente
196
+ Para acessar minha conta com segurança
197
+
198
+ [CONTEXT]
199
+ Dado que estou na tela de login
157
200
 
158
201
  [SUCCESS]
159
- Quando preencho <email> e <senha>
202
+ Quando preencho email e senha válidos
160
203
  Então vejo a tela inicial
161
204
 
205
+ [SUCCESS]
206
+ Quando tento logar com "<email>" e "<senha>"
207
+ Então recebo "<mensagem>"
208
+
209
+ [EXAMPLES]
210
+ | email | senha | mensagem |
211
+ | user@site.com | 123456 | login realizado |
212
+ | errado@site.com | senha | credenciais inválidas |
213
+ | | senha | email é obrigatório |
214
+ | user@site.com | | senha é obrigatória |
215
+
216
+ [SUCCESS]
217
+ Quando deixo o campo "<campo>" vazio
218
+ Então recebo a mensagem "<mensagem>"
219
+
162
220
  [EXAMPLES]
163
- | email | senha |
164
- | user@site.com | 123456 |
165
- | errado@site.com | senha |
221
+ | campo | mensagem |
222
+ | | login realizado |
223
+ | | credenciais inválidas |
224
+ | email | email é obrigatório |
225
+ | senha | senha é obrigatória |
166
226
  ```
167
227
 
168
228
  ---
data/Rakefile CHANGED
@@ -1,49 +1,36 @@
1
- # Rakefile
2
- require_relative 'lib/env'
3
1
  require 'rake'
2
+ require 'bddgenx'
4
3
 
5
4
  namespace :bddgenx do
6
- desc 'Inicializar projeto'
7
- task :setup do
8
- Bddgenx::Setup.inicializar_projeto
9
- end
10
-
11
- desc 'Executa a geração BDD usando o modo atual (static, chatgpt, gemini)'
5
+ desc 'Executa geração interativa: escolha entre static, chatgpt, gemini ou deepseek'
12
6
  task :generate do
13
- puts "⚙️ Modo de geração: #{Bddgenx.configuration.mode}"
7
+ puts "=== Qual modo deseja usar para gerar os cenários? ==="
8
+ puts "1. static (sem IA)"
9
+ puts "2. chatgpt (via OpenAI)"
10
+ puts "3. gemini (via Google)"
11
+ print "Digite o número (1-3): "
14
12
 
15
- # Evita que ARGV contenha o nome da task (como "bddgenx:static")
16
- ARGV.clear
13
+ escolha = STDIN.gets.chomp.to_i
17
14
 
18
- Bddgenx::Runner.execute
19
- end
20
-
21
- desc 'Gera features no modo estático (sem IA)'
22
- task :static do
23
- Bddgenx.configure do |config|
24
- config.mode = :static
25
- end
26
- ENV['BDDGENX_MODE'] = 'static'
27
- Rake::Task['bddgenx:generate'].invoke
28
- end
15
+ modo = case escolha
16
+ when 1 then :static
17
+ when 2 then :chatgpt
18
+ when 3 then :gemini
19
+ else
20
+ puts "❌ Opção inválida. Saindo."; exit 1
21
+ end
29
22
 
30
- desc 'Gera features usando ChatGPT'
31
- task :chatgpt do
32
23
  Bddgenx.configure do |config|
33
- config.mode = :chatgpt
24
+ config.mode = modo
34
25
  config.openai_api_key_env = 'OPENAI_API_KEY'
35
- end
36
- ENV['BDDGENX_MODE'] = 'chatgpt'
37
- Rake::Task['bddgenx:generate'].invoke
38
- end
39
-
40
- desc 'Gera features usando Gemini'
41
- task :gemini do
42
- Bddgenx.configure do |config|
43
- config.mode = :gemini
44
26
  config.gemini_api_key_env = 'GEMINI_API_KEY'
45
27
  end
46
- ENV['BDDGENX_MODE'] = 'gemini'
47
- Rake::Task['bddgenx:generate'].invoke
28
+
29
+ # ⚠️ Limpa o ARGV antes de executar para evitar que [static] seja interpretado como nome de arquivo
30
+ ARGV.clear
31
+
32
+ ENV['BDDGENX_MODE'] = modo.to_s
33
+ puts "\n⚙️ Modo selecionado: #{modo}\n\n"
34
+ Bddgenx::Runner.execute
48
35
  end
49
36
  end
data/VERSION CHANGED
@@ -1 +1 @@
1
- 2.3.1
1
+ 2.3.3
@@ -101,15 +101,18 @@ module Bddgenx
101
101
  end
102
102
 
103
103
  # Geração de feature
104
- if modo == 'gemini' || modo == 'chatgpt'
104
+ if %w[gemini chatgpt].include?(modo)
105
105
  puts "🤖 Gerando cenários com IA (#{modo.capitalize})..."
106
106
  idioma = IA::GeminiCliente.detecta_idioma_arquivo(arquivo)
107
- feature_text =
107
+
108
+ feature_text = Bddgenx::Support::Loader.run("⏳ Aguardando resposta da IA...") do
108
109
  if modo == 'gemini'
109
110
  IA::GeminiCliente.gerar_cenarios(historia, idioma)
110
111
  else
111
112
  IA::ChatGptCliente.gerar_cenarios(historia, idioma)
112
113
  end
114
+ end
115
+
113
116
  if feature_text
114
117
  feature_path = Generator.path_para_feature(arquivo)
115
118
  feature_content = Bddgenx::GherkinCleaner.limpar(feature_text)
@@ -119,7 +122,9 @@ module Bddgenx
119
122
  next
120
123
  end
121
124
  else
122
- feature_path, feature_content = Generator.gerar_feature(historia)
125
+ feature_path, feature_content = Bddgenx::Support::Loader.run("⛏️ Gerando feature estática...", :dots) do
126
+ Generator.gerar_feature(historia)
127
+ end
123
128
  end
124
129
 
125
130
  Backup.salvar_versao_antiga(feature_path)
@@ -55,21 +55,31 @@ module Bddgenx
55
55
 
56
56
  # Prompt base enviado ao ChatGPT, instruindo a saída no formato correto
57
57
  prompt_base = <<~PROMPT
58
- Gere cenários BDD no formato Gherkin, usando as palavras-chave de estrutura no idioma \"#{idioma}\":
59
- Feature: #{keywords[:feature]}
60
- Scenario: #{keywords[:scenario]}
61
- Scenario Outline: #{keywords[:scenario_outline]}
62
- Examples: #{keywords[:examples]}
63
- Given: #{keywords[:given]}
64
- When: #{keywords[:when]}
65
- Then: #{keywords[:then]}
66
- And: #{keywords[:and]}
67
-
68
- Atenção: Os textos e descrições dos cenários e passos devem ser escritos em português, mesmo que as palavras-chave estejam em inglês.
69
-
70
- História:
71
- #{historia}
72
- PROMPT
58
+ Gere cenários BDD no formato Gherkin, utilizando as palavras-chave estruturais no idioma "#{idioma}":
59
+ Feature: #{keywords[:feature]}
60
+ Scenario: #{keywords[:scenario]}
61
+ Scenario Outline: #{keywords[:scenario_outline]}
62
+ Examples: #{keywords[:examples]}
63
+ Given: #{keywords[:given]}
64
+ When: #{keywords[:when]}
65
+ Then: #{keywords[:then]}
66
+ And: #{keywords[:and]}
67
+
68
+ Instruções:
69
+ - Todos os textos dos passos devem ser escritos em **português**.
70
+ - Use as palavras-chave Gherkin no idioma especificado ("#{idioma}").
71
+ - Gere **vários cenários**, incluindo positivos e negativos.
72
+ - Use `Scenario Outline` e `Examples` sempre que houver valores variáveis.
73
+ - Mantenha os parâmetros como `<email>`, `<senha>` e outros entre colchetes angulares, exatamente como aparecem.
74
+ - Se a história fornecer contexto (ex: `[CONTEXT]` ou "Dado que..."), utilize-o como base para os cenários.
75
+ - Se não houver contexto explícito, **crie um coerente** baseado na história.
76
+ - A primeira linha do resultado deve conter obrigatoriamente `# language: #{idioma}`.
77
+ - Evite passos vagos ou genéricos. Use ações claras e específicas.
78
+ - Gere apenas o conteúdo da feature, sem explicações adicionais.
79
+
80
+ História fornecida:
81
+ #{historia}
82
+ PROMPT
73
83
 
74
84
  uri = URI(CHATGPT_API_URL)
75
85
  request_body = {
@@ -107,7 +117,10 @@ module Bddgenx
107
117
  return fallback_com_gemini(historia, idioma)
108
118
  end
109
119
  else
110
- warn "❌ Erro ao chamar ChatGPT: #{response.code} - #{response.body}"
120
+ if response.code.to_i == 429
121
+ warn "❌ Limite de uso da API OpenAI excedido."
122
+ warn "🔗 Verifique sua conta: https://platform.openai.com/account/usage"
123
+ end
111
124
  return fallback_com_gemini(historia, idioma)
112
125
  end
113
126
  end
@@ -46,21 +46,33 @@ module Bddgenx
46
46
 
47
47
  # Prompt base que instrui a IA a gerar cenários Gherkin no idioma indicado
48
48
  prompt_base = <<~PROMPT
49
- Gere cenários BDD no formato Gherkin, usando as palavras-chave de estrutura no idioma "#{idioma}":
50
- Feature: #{keywords[:feature]}
51
- Scenario: #{keywords[:scenario]}
52
- Scenario Outline: #{keywords[:scenario_outline]}
53
- Examples: #{keywords[:examples]}
54
- Given: #{keywords[:given]}
55
- When: #{keywords[:when]}
56
- Then: #{keywords[:then]}
57
- And: #{keywords[:and]}
58
-
59
- Atenção: Os textos e descrições dos cenários e passos devem ser escritos em português, mesmo que as palavras-chave estejam em inglês.
60
-
61
- História:
62
- #{historia}
63
- PROMPT
49
+ Gere cenários BDD no formato Gherkin, utilizando as palavras-chave estruturais no idioma "#{idioma}":
50
+ Feature: #{keywords[:feature]}
51
+ Scenario: #{keywords[:scenario]}
52
+ Scenario Outline: #{keywords[:scenario_outline]}
53
+ Examples: #{keywords[:examples]}
54
+ Given: #{keywords[:given]}
55
+ When: #{keywords[:when]}
56
+ Then: #{keywords[:then]}
57
+ And: #{keywords[:and]}
58
+
59
+ Instruções:
60
+ - Todos os textos dos passos devem ser escritos em **português**.
61
+ - Use as palavras-chave Gherkin no idioma especificado ("#{idioma}").
62
+ - Gere **vários cenários**, incluindo positivos e negativos.
63
+ - Use `Scenario Outline` e `Examples` sempre que houver valores variáveis.
64
+ - Mantenha os parâmetros como `<email>`, `<senha>` e outros entre colchetes angulares, exatamente como aparecem.
65
+ - Se a história fornecer contexto (ex: `[CONTEXT]` ou "Dado que..."), utilize-o como base para os cenários.
66
+ - Se não houver contexto explícito, **crie um coerente** baseado na história.
67
+ - A primeira linha do resultado deve conter obrigatoriamente `# language: #{idioma}`.
68
+ - Evite passos vagos ou genéricos. Use ações claras e específicas.
69
+ - Gere apenas o conteúdo da feature, sem explicações adicionais.
70
+
71
+ História fornecida:
72
+ #{historia}
73
+ PROMPT
74
+
75
+
64
76
 
65
77
  unless api_key
66
78
  warn "❌ API Key do Gemini não encontrada no .env (GEMINI_API_KEY)"
@@ -101,6 +113,11 @@ module Bddgenx
101
113
  texto_limpo.sub!(/^# language: .*/, "# language: #{idioma}")
102
114
  texto_limpo.prepend("# language: #{idioma}\n") unless texto_limpo.start_with?("# language:")
103
115
 
116
+ # Garante diretiva de idioma
117
+ feature_text = Bddgenx::GherkinCleaner.limpar(texto_ia)
118
+ feature_text.sub!(/^# language: .*/, "") # remove qualquer # language: existente
119
+ feature_text.prepend("# language: #{idioma}\n") # insere a correta
120
+
104
121
  return texto_limpo
105
122
  else
106
123
  warn "❌ Resposta da IA sem conteúdo de texto"
@@ -0,0 +1,26 @@
1
+ #!/usr/bin/env ruby
2
+ module Bddgenx
3
+ class Setup
4
+ def self.inicializar_projeto
5
+ puts "🔧 Configurando ambiente do projeto BddGenX..."
6
+
7
+ # Cria .env a partir do exemplo
8
+ if File.exist?(".env")
9
+ puts "✅ .env já existe. Nada a fazer."
10
+ else
11
+ if File.exist?(".env.example")
12
+ FileUtils.cp(".env.example", ".env")
13
+ puts "✅ .env criado a partir de .env.example"
14
+ else
15
+ puts "⚠️ Arquivo .env.example não encontrado. Crie manualmente o .env"
16
+ end
17
+ end
18
+
19
+ # Garante existência do diretório de input
20
+ FileUtils.mkdir_p("input")
21
+ puts "📂 Pasta input criada (se necessário)."
22
+
23
+ puts "\n✅ Setup completo! Agora edite o arquivo `.env` e adicione suas chaves de API."
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,31 @@
1
+ module Bddgenx
2
+ module Support
3
+ class Loader
4
+ SPINNERS = {
5
+ default: %w[| / - \\],
6
+ dots: %w[⠋ ⠙ ⠹ ⠸ ⠼ ⠴ ⠦ ⠧ ⠇ ⠏]
7
+ }
8
+
9
+ def self.run(mensagem = "⏳ Processando...", tipo = :default)
10
+ spinner = SPINNERS[tipo] || SPINNERS[:default]
11
+ done = false
12
+
13
+ thread = Thread.new do
14
+ i = 0
15
+ print "\n"
16
+ until done
17
+ print "\r#{mensagem} #{spinner[i % spinner.length]}"
18
+ sleep(0.1)
19
+ i += 1
20
+ end
21
+ end
22
+
23
+ result = yield
24
+ done = true
25
+ thread.join
26
+ print "\r#{mensagem} ✅\n"
27
+ result
28
+ end
29
+ end
30
+ end
31
+ end
data/lib/env.rb CHANGED
@@ -45,7 +45,8 @@ require_relative 'bddgenx/reports/backup' # Mecanismo de bac
45
45
  require_relative 'bddgenx/reports/tracer' # Rastreabilidade dos processos
46
46
 
47
47
  require_relative 'bddgenx/configuration' # Configuração das variaveis de IA
48
- require_relative '../bin/setup' # Verifica estrutura do projeto, caso nao exista cria a nova.
48
+ require_relative 'bddgenx/setup' # Verifica estrutura do projeto, caso nao exista cria a nova.
49
+ require_relative 'bddgenx/support/loader'
49
50
 
50
51
  # Define variável de ambiente global para indicar que o ambiente BDDGENX está em modo desenvolvimento
51
52
  ENV['BDDGENX_ENV'] = 'development'
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: bddgenx
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.3.1
4
+ version: 2.3.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - David Nascimento
@@ -135,8 +135,10 @@ files:
135
135
  - lib/bddgenx/reports/backup.rb
136
136
  - lib/bddgenx/reports/pdf_exporter.rb
137
137
  - lib/bddgenx/reports/tracer.rb
138
+ - lib/bddgenx/setup.rb
138
139
  - lib/bddgenx/support/font_loader.rb
139
140
  - lib/bddgenx/support/gherkin_cleaner.rb
141
+ - lib/bddgenx/support/loader.rb
140
142
  - lib/bddgenx/support/remover_steps_duplicados.rb
141
143
  - lib/bddgenx/support/validator.rb
142
144
  - lib/bddgenx/version.rb