victormottatz commited on
Commit
5325588
·
verified ·
1 Parent(s): 4567be3

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +10 -239
app.py CHANGED
@@ -1,32 +1,24 @@
1
-
2
- """Imovel.ipynb
3
- Automatically generated by Colab.
4
- Original file is located at
5
- https://colab.research.google.com/drive/1DZAQZfrXvTy358Vg2qfUg_ge6b3kcgBy
6
- """
7
-
8
- # app.py
9
  import pandas as pd
10
  import requests
11
  import io
12
  import itertools
13
  from collections import defaultdict
14
  import gradio as gr
15
- import time
16
 
17
  # 🔧 CONFIGURAÇÕES GLOBAIS
18
- # Certifique-se de que este FILE_ID esteja acessível publicamente ou para "Qualquer pessoa com o link"
19
- FILE_ID = "1XvNz7DlWioT64uNdcfBSL8Ui2nRSi9gT"
20
  URL = f"https://drive.google.com/uc?export=download&id={FILE_ID}"
21
 
22
  # Variável global para armazenar o DataFrame
23
  df = None
24
 
25
  def carregar_planilha():
26
- """Carrega e prepara a planilha para análise."""
27
  global df
28
  try:
29
- print("⏳ Carregando planilha...")
30
  response = requests.get(URL)
31
  response.raise_for_status()
32
  data = io.BytesIO(response.content)
@@ -35,230 +27,9 @@ def carregar_planilha():
35
  # Padroniza nomes das colunas
36
  df.columns = df.columns.str.strip().str.lower().str.replace(" ", "_")
37
 
38
- # Converte colunas numéricas
39
- colunas_numericas = ['valor_credito', 'valor_entrada', 'valor_parcela', 'saldo_devedor', 'qtd_parcelas']
40
- for coluna in colunas_numericas:
41
- if coluna in df.columns:
42
- df[coluna] = pd.to_numeric(df[coluna], errors='coerce').fillna(0)
43
-
44
- # Verifica colunas essenciais
45
- if 'tipo_do_bem' not in df.columns or 'administradora' not in df.columns:
46
- raise ValueError("Colunas essenciais não encontradas")
47
-
48
- # Remove duplicatas
49
- df.drop_duplicates(inplace=True)
50
-
51
- print("✅ Planilha carregada com sucesso")
52
- return True
53
-
54
- except Exception as e:
55
- print(f"❌ Erro ao carregar planilha: {str(e)}")
56
- return False
57
-
58
- def agrupar_por_administradora(dataframe):
59
- """Agrupa cotas por administradora."""
60
- grupos = defaultdict(list)
61
- for _, row in dataframe.iterrows():
62
- grupos[row['administradora']].append(row.to_dict())
63
- return grupos
64
-
65
- def buscar_combinacoes(credito_desejado, entrada_desejada, parcela_desejada, administradoras=None):
66
- """Busca combinações de cotas dentro dos parâmetros especificados."""
67
- # Garante que o DataFrame está carregado
68
- if df is None:
69
- # Tenta carregar se ainda não foi carregado
70
- if not carregar_planilha():
71
- return "❌ Erro: Planilha não carregada. Por favor, tente novamente."
72
-
73
- # Filtra por tipo de bem e administradoras
74
- df_filtrado = df[df['tipo_do_bem'].str.lower() == 'imovel']
75
- if administradoras:
76
- # Certifica-se de que administradoras é uma lista (Gradio retorna tupla)
77
- if isinstance(administradoras, tuple):
78
- administradoras = list(administradoras)
79
- df_filtrado = df_filtrado[df_filtrado['administradora'].isin(administradoras)]
80
-
81
- if df_filtrado.empty:
82
- return "🚫 Nenhuma cota encontrada com os filtros aplicados. Tente ajustar os parâmetros."
83
-
84
- # Define faixas de tolerância
85
- credito_min, credito_max = credito_desejado * 0.93, credito_desejado * 1.07
86
- entrada_min, entrada_max = entrada_desejada * 0.93, entrada_desejada * 1.07
87
- parcela_min, parcela_max = parcela_desejada * 0.75, parcela_desejada * 1.25
88
-
89
- grupos = agrupar_por_administradora(df_filtrado)
90
- resultados = []
91
-
92
- for adm, cotas in grupos.items():
93
- for r in range(1, min(3, len(cotas)) + 1): # Máximo 3 cotas por combinação
94
- for combinacao in itertools.combinations(cotas, r):
95
- total_credito = sum(c['valor_credito'] for c in combinacao)
96
- total_entrada = sum(c['valor_entrada'] for c in combinacao)
97
- total_parcelas = sum(c['valor_parcela'] for c in combinacao)
98
-
99
- if (credito_min <= total_credito <= credito_max and
100
- entrada_min <= total_entrada <= entrada_max and
101
- parcela_min <= total_parcelas <= parcela_max):
102
-
103
- total_saldo = sum(c['saldo_devedor'] for c in combinacao)
104
- valor_final = round(total_entrada + total_saldo, 2)
105
- diferenca = abs(valor_final - total_credito) # Diferença do valor final pelo crédito (para ordenação)
106
-
107
- resultados.append((adm, combinacao, diferenca))
108
-
109
- if not resultados:
110
- return "🚫 Nenhuma combinação adequada encontrada com os parâmetros fornecidos."
111
 
112
- resultados.sort(key=lambda x: x[2]) # Ordena pela diferença
113
-
114
- return formatar_resultados(resultados)
115
-
116
- def formatar_moeda(valor):
117
- return f"R$ {valor:,.2f}".replace(",", "v").replace(".", ",").replace("v", ".")
118
-
119
- def formatar_resultados(resultados):
120
- """Formata os resultados para exibição."""
121
- resposta = ""
122
- # Limita a 15 resultados para evitar saídas muito longas
123
- for idx, (adm, combinacao, _) in enumerate(resultados[:15], 1):
124
- codigos = [str(c.get('codigo', 'N/A')) for c in combinacao]
125
- total_credito = sum(c['valor_credito'] for c in combinacao)
126
- total_entrada = sum(c['valor_entrada'] for c in combinacao)
127
- total_saldo = sum(c['saldo_devedor'] for c in combinacao)
128
- total_parcelas = sum(c['valor_parcela'] for c in combinacao)
129
- maior_prazo = max(int(c.get('qtd_parcelas', 0)) for c in combinacao)
130
-
131
- valor_final = round(total_entrada + total_saldo, 2)
132
- credito_real = round(total_credito - total_entrada, 2)
133
- taxa_total = total_saldo - credito_real
134
- taxa_percentual = (taxa_total / credito_real) * 100 if credito_real > 0 else 0
135
- taxa_mensal = taxa_percentual / maior_prazo if maior_prazo > 0 else 0
136
-
137
- resposta += f"""
138
- --- COMBINAÇÃO {idx} ---
139
- 🏢 Administradora: {adm}
140
- 🔢 Códigos: {', '.join(codigos)}
141
- 💰 Crédito Total: {formatar_moeda(total_credito)}
142
- 💵 Entrada (+comissão): {formatar_moeda(total_entrada)}
143
- 📉 Saldo Devedor: {formatar_moeda(total_saldo)}
144
- 💲 Parcela: {formatar_moeda(total_parcelas)}
145
- ⏳ Prazo: {maior_prazo} meses
146
- 🔚 Valor Final: {formatar_moeda(valor_final)}
147
- 💠 Crédito Líquido: {formatar_moeda(credito_real)}
148
- 📊 Taxa Total: {taxa_percentual:.2f}% ({formatar_moeda(taxa_total)})
149
- 🗓️ Taxa Mensal: {taxa_mensal:.2f}%
150
- 🗓️ Taxa Anual: {taxa_mensal * 12:.2f}%
151
- """
152
- return resposta
153
-
154
- # Carrega a planilha uma vez quando o aplicativo inicia
155
- carregar_planilha()
156
-
157
- # Prepara a lista de administradoras para o Gradio
158
- def get_administradoras_options():
159
- if df is not None:
160
- adm_list = df[df['tipo_do_bem'].str.lower() == 'imovel']['administradora'].unique()
161
- return sorted(adm_list)
162
- return []
163
-
164
- # Criando a interface Gradio
165
- with gr.Blocks(title="Sistema de Busca de Consórcio Imóvel") as demo:
166
- gr.HTML("""
167
- <link href="https://fonts.googleapis.com/css2?family=Poppins&display=swap" rel="stylesheet">
168
- <style>
169
- * {
170
- font-family: 'Poppins', sans-serif !important;
171
- }
172
-
173
- body {
174
- background-color: #ff8f00 !important;
175
- color: black !important;
176
- }
177
-
178
- /* Inputs Numéricos: Crédito, Entrada, Parcela */
179
- input[type="number"] {
180
- background-color: white !important;
181
- border: 2px solid #000 !important;
182
- border-radius: 12px !important;
183
- color: black !important;
184
- padding: 10px !important;
185
- font-weight: 500;
186
- }
187
-
188
- /* Inputs de texto e áreas de texto (como a saída e código) */
189
- input[type="text"], textarea {
190
- background-color: white !important;
191
- border: 2px solid black !important;
192
- border-radius: 12px !important;
193
- color: black !important;
194
- padding: 10px !important;
195
- }
196
-
197
- input::placeholder, textarea::placeholder {
198
- color: #333 !important;
199
- opacity: 0.7;
200
- }
201
-
202
- .gr-checkbox label {
203
- display: flex;
204
- align-items: center;
205
- gap: 8px;
206
- font-weight: 600;
207
- }
208
-
209
- input[type="checkbox"] {
210
- accent-color: black !important;
211
- width: 18px;
212
- height: 18px;
213
- }
214
-
215
- .gr-button {
216
- font-weight: bold;
217
- border-radius: 10px !important;
218
- background-color: white !important;
219
- color: black !important;
220
- border: 2px solid black !important;
221
- }
222
-
223
- .gr-button:hover {
224
- background-color: #fff3e0 !important;
225
- color: black !important;
226
- }
227
-
228
- label {
229
- font-weight: 600 !important;
230
- }
231
- </style>
232
- """)
233
-
234
-
235
- gr.Markdown("# 🏠 Busca de Combinações de Consórcio Imóvel")
236
- gr.Markdown("Insira os valores desejados para crédito, entrada e parcela, e filtre por administradora.")
237
-
238
- with gr.Row():
239
- credito_input = gr.Number(label="Crédito Desejado (R$)", value=300000, step=1000)
240
- entrada_input = gr.Number(label="Entrada Desejada (R$)", value=30000, step=1000)
241
- parcela_input = gr.Number(label="Parcela Desejada (R$)", value=1500, step=100)
242
-
243
- administradoras_multiselect = gr.CheckboxGroup(
244
- label="Filtrar por Administradoras",
245
- choices=get_administradoras_options(),
246
- value=get_administradoras_options() # Seleciona todas por padrão
247
- )
248
-
249
- submit_btn = gr.Button("🔍 Buscar Combinações", variant="primary")
250
-
251
- output_text = gr.Textbox(label="Resultados da Busca", lines=20, max_lines=40, interactive=False, placeholder="Os resultados aparecerão aqui...")
252
-
253
- submit_btn.click(
254
- fn=buscar_combinacoes,
255
- inputs=[credito_input, entrada_input, parcela_input, administradoras_multiselect],
256
- outputs=output_text
257
- )
258
-
259
- gr.Markdown("---")
260
- gr.Markdown("Desenvolvido para auxiliar na busca por cotas de consórcio ideais.")
261
-
262
- # Inicia o aplicativo Gradio
263
- if __name__ == "__main__":
264
- demo.launch() # Você não precisa disso no Colab, mas sim no arquivo que você fará o deploy
 
1
+ # -- coding: utf-8 --
2
+ """Robô de Cálculo para Consórcio de Imóveis - Versão Ajustada"""
 
 
 
 
 
 
3
  import pandas as pd
4
  import requests
5
  import io
6
  import itertools
7
  from collections import defaultdict
8
  import gradio as gr
 
9
 
10
  # 🔧 CONFIGURAÇÕES GLOBAIS
11
+ FILE_ID = "1XvNz7DlWioT64uNdcfBSL8Ui2nRSi9gT" # Substitua pelo ID correto da planilha de imóveis
 
12
  URL = f"https://drive.google.com/uc?export=download&id={FILE_ID}"
13
 
14
  # Variável global para armazenar o DataFrame
15
  df = None
16
 
17
  def carregar_planilha():
18
+ """Carrega e prepara a planilha para análise de consórcios de imóveis."""
19
  global df
20
  try:
21
+ print("⏳ Carregando planilha de imóveis...")
22
  response = requests.get(URL)
23
  response.raise_for_status()
24
  data = io.BytesIO(response.content)
 
27
  # Padroniza nomes das colunas
28
  df.columns = df.columns.str.strip().str.lower().str.replace(" ", "_")
29
 
30
+ # Padroniza os nomes das administradoras
31
+ if 'administradora' in df.columns:
32
+ df['administradora'] = df['administradora'].astype(str).str.strip().str.lower()
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
33
 
34
+ # Converte colunas numéricas
35
+ numeric_cols = ['valor_credito', 'valor_entrada', 'valor_parcela', 'saldo_deve