feat: adicionar sistema de sugestao de consultores por tema
- Novo endpoint GET /api/v1/consultores/sugerir com busca por tema - Busca inteligente em areas de avaliacao, conhecimento e pesquisa - Filtro por consultores ativos e area de avaliacao especifica - Endpoint GET /api/v1/consultores/areas-avaliacao com lista de areas - Novo componente SugerirConsultores no frontend - Botao 'Sugerir por Tema' integrado na interface principal - Score de match baseado em relevancia do tema e experiencia
This commit is contained in:
@@ -24,6 +24,9 @@ from ..schemas.ranking_schema import (
|
||||
ProcessarRankingResponseSchema,
|
||||
ConsultaNomeSchema,
|
||||
PosicaoRankingSchema,
|
||||
SugestaoConsultorSchema,
|
||||
SugerirConsultoresResponseSchema,
|
||||
AreaAvaliacaoSchema,
|
||||
)
|
||||
from .dependencies import get_repository, get_ranking_store, get_processar_job, get_es_client
|
||||
from ...infrastructure.elasticsearch.client import ElasticsearchClient
|
||||
@@ -410,3 +413,99 @@ async def exportar_ficha_pdf(
|
||||
"Content-Disposition": f'attachment; filename="{nome_arquivo}"'
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
@router.get("/consultores/sugerir", response_model=SugerirConsultoresResponseSchema)
|
||||
async def sugerir_consultores(
|
||||
tema: str = Query(..., min_length=2, description="Tema ou assunto para buscar consultores"),
|
||||
area_avaliacao: Optional[str] = Query(None, description="Filtrar por area de avaliacao especifica"),
|
||||
apenas_ativos: bool = Query(True, description="Filtrar apenas consultores ativos"),
|
||||
quantidade: int = Query(20, ge=1, le=100, description="Quantidade maxima de sugestoes"),
|
||||
es_client: ElasticsearchClient = Depends(get_es_client),
|
||||
store = Depends(get_ranking_store),
|
||||
):
|
||||
try:
|
||||
resultados = await es_client.sugerir_consultores(
|
||||
tema=tema,
|
||||
area_avaliacao=area_avaliacao,
|
||||
apenas_ativos=apenas_ativos,
|
||||
size=quantidade
|
||||
)
|
||||
|
||||
consultores = []
|
||||
for doc in resultados:
|
||||
id_pessoa = doc.get("id")
|
||||
nome = doc.get("dadosPessoais", {}).get("nome", "")
|
||||
score_match = doc.get("_score_match", 0)
|
||||
|
||||
areas_avaliacao = set()
|
||||
areas_conhecimento = set()
|
||||
linhas_pesquisa = set()
|
||||
situacao = ""
|
||||
ies = None
|
||||
foi_coordenador = False
|
||||
foi_premiado = False
|
||||
|
||||
for atuacao in doc.get("atuacoes", []):
|
||||
tipo = atuacao.get("tipo", "")
|
||||
|
||||
if tipo == "Consultor":
|
||||
dados = atuacao.get("dadosConsultoria", {})
|
||||
situacao = dados.get("situacaoConsultoria", "")
|
||||
if dados.get("ies"):
|
||||
ies = dados["ies"].get("sigla") or dados["ies"].get("nome")
|
||||
|
||||
for area in dados.get("areaConhecimentoPos", []):
|
||||
if area.get("nome"):
|
||||
areas_conhecimento.add(area["nome"])
|
||||
area_aval = area.get("areaAvaliacao", {})
|
||||
if area_aval and area_aval.get("nome"):
|
||||
areas_avaliacao.add(area_aval["nome"])
|
||||
|
||||
for pesq in dados.get("areaPesquisa", []):
|
||||
if pesq.get("descricao"):
|
||||
linhas_pesquisa.add(pesq["descricao"])
|
||||
|
||||
elif "Coordenação" in tipo:
|
||||
foi_coordenador = True
|
||||
|
||||
elif "Premiação" in tipo:
|
||||
foi_premiado = True
|
||||
|
||||
posicao_ranking = None
|
||||
if store.is_ready():
|
||||
entry = store.get_by_id(id_pessoa)
|
||||
if entry:
|
||||
posicao_ranking = entry.posicao
|
||||
|
||||
consultores.append(SugestaoConsultorSchema(
|
||||
id_pessoa=id_pessoa,
|
||||
nome=nome,
|
||||
score_match=score_match,
|
||||
areas_avaliacao=list(areas_avaliacao),
|
||||
areas_conhecimento=list(areas_conhecimento),
|
||||
linhas_pesquisa=list(linhas_pesquisa),
|
||||
situacao=situacao,
|
||||
ies=ies,
|
||||
foi_coordenador=foi_coordenador,
|
||||
foi_premiado=foi_premiado,
|
||||
))
|
||||
|
||||
return SugerirConsultoresResponseSchema(
|
||||
tema_buscado=tema,
|
||||
total_encontrados=len(consultores),
|
||||
consultores=consultores
|
||||
)
|
||||
except Exception as e:
|
||||
raise HTTPException(status_code=500, detail=f"Erro ao sugerir consultores: {str(e)}")
|
||||
|
||||
|
||||
@router.get("/consultores/areas-avaliacao", response_model=List[AreaAvaliacaoSchema])
|
||||
async def listar_areas_avaliacao(
|
||||
es_client: ElasticsearchClient = Depends(get_es_client),
|
||||
):
|
||||
try:
|
||||
areas = await es_client.listar_areas_avaliacao()
|
||||
return [AreaAvaliacaoSchema(**a) for a in areas]
|
||||
except Exception as e:
|
||||
raise HTTPException(status_code=500, detail=f"Erro ao listar areas de avaliacao: {str(e)}")
|
||||
|
||||
Reference in New Issue
Block a user