Post-IA-08
Uso de IA na criação de um webapp – Part 7
Definido a melhor estrutura para nosso app e criando os programas
Formato do blog
Prompts em azul,
Meus comentários em verde,
Soluções da IA em preto,
Comentários da IA em marrom.
IAs Utilizadas neste Post
Copilot
No post anterior, exploramos diferentes estratégias de reconhecimento facial e avaliamos suas vantagens e limitações. A partir dessa análise, optamos por utilizar uma biblioteca real para realizar tanto o reconhecimento quanto o cadastramento de rostos no nosso aplicativo.
Concluímos que a melhor abordagem para o nosso projeto seria estruturar a solução em três partes principais:
Dois programas de frontend: CadastroRosto.jsx e RegistroPonto.jsx
Uma API de backend: app.py
No frontend, utilizamos React para construir a interface e integrar o reconhecimento facial. Para definir a melhor linguagem para o backend, consultamos o Copilot. Com base em critérios como privacidade, desempenho e facilidade de integração com bibliotecas de IA, optamos por desenvolver a API em Python, utilizando o framework Flask e persistência local em JSON.
Você poderia recomendar-me qual seria a melhor linguagem para criar o backend?
✅ Existem bastante vantagens de usar Python para reconhecimento facial no backend
🧠 1. Ecossistema de IA maduro — Python é a linguagem dominante em IA e ciência de dados.
Tem bibliotecas robustas como numpy, scikit-learn, face_recognition, dlib, opencv, etc.
📏 2. Comparação vetorial eficiente — com numpy, você pode calcular distância euclidiana entre vetores com uma linha de código:
np.linalg.norm(vetor1 - vetor2)
🧪 3. Integração com modelos avançados — pode usar face_recognition (baseado em dlib) e frameworks como FastAPI ou Flask.
🔐 4. Privacidade e controle — o backend recebe apenas o vetor facial, sem imagens, com total segurança.
Com base nas decisões anteriores — especialmente a escolha por realizar o reconhecimento facial localmente e a comparação de vetores na nuvem — emitimos o seguinte prompt para o Copilot:
Queremos criar uma solução de registro de ponto com reconhecimento facial, onde o vetor facial é gerado no dispositivo do usuário e enviado para uma API Flask que realiza a comparação com vetores previamente cadastrados. A persistência será feita em JSON. Como deve ser estruturado esse projeto?
A partir desse prompt, o Copilot nos ajudou a definir uma arquitetura clara e escalável:
Frontend React — dois componentes:
CadastroRosto.jsx: captura o rosto, gera o vetor facial e envia junto com os dados do usuário.
RegistroPonto.jsx: reconhece o usuário com base no vetor facial e registra o ponto.
Backend Flask — persistência em JSON:
Endpoint /cadastrar e /reconhecer para armazenar e comparar vetores.
Essa estrutura mantém a privacidade e é escalável, ideal para aplicações reais.
Vamos então criar API Flask + React separados para backend e frontend. Você poderia criar uma estrutura que suportasse essa solução?
Estrutura recomendada do projeto
controle-ponto/ ├── frontend/ │ ├── src/components/ │ │ ├── RegistroPonto.jsx │ │ └── CadastroRosto.jsx │ ├── services/api.js │ ├── App.jsx │ └── main.jsx │ ├── backend/ │ ├── app.py │ ├── usuarios.json │ ├── face_utils.py │ ├── requirements.txt │ └── README.md
Crie então o programa CadastroRosto.jsx
📄 CadastroRosto.jsx — captura o vetor facial localmente e envia ao backend via API Flask.
<code>
import { useState, useEffect, useRef } from "react";
import * as faceapi from "face-api.js";
const CadastroRosto = () => {
const videoRef = useRef(null);
const [nome, setNome] = useState("");
const [status, setStatus] = useState("");
const loadModels = async () => {
const MODEL_URL = "/models";
await Promise.all([
faceapi.nets.ssdMobilenetv1.loadFromUri(MODEL_URL),
faceapi.nets.faceLandmark68Net.loadFromUri(MODEL_URL),
faceapi.nets.faceRecognitionNet.loadFromUri(MODEL_URL),
]);
};
const startVideo = async () => {
const stream = await navigator.mediaDevices.getUserMedia({ video: true });
videoRef.current.srcObject = stream;
};
const enviarParaBackend = async (nome, descriptor) => {
try {
const response = await fetch("http://localhost:5000/cadastrar", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ nome, descriptor }),
});
const result = await response.json();
if (result.status === "ok") {
setStatus(`✅ Rosto de "${nome}" cadastrado com sucesso.`);
} else {
setStatus("❌ Erro ao cadastrar rosto.");
}
} catch (error) {
setStatus("❌ Falha de comunicação.");
}
};
const capturarRosto = async () => {
setStatus("Detectando rosto...");
const detection = await faceapi
.detectSingleFace(videoRef.current)
.withFaceLandmarks()
.withFaceDescriptor();
if (detection) {
await enviarParaBackend(nome, detection.descriptor);
setNome("");
} else {
setStatus("❌ Nenhum rosto detectado.");
}
};
useEffect(() => {
loadModels().then(startVideo);
}, []);
return (
<div>
<h2>Cadastro de Rosto</h2>
<video ref={videoRef} autoPlay />
<input value={nome} onChange={(e) => setNome(e.target.value)} />
<button onClick={capturarRosto}>Cadastrar</button>
<p>{status}</p>
</div>
);
};
export default CadastroRosto;
</code>
Agora crie a API Flask em Python para testar o CadastroRosto.jsx, usando JSON para persistir os vetores.
app.py — backend Flask que cadastra e reconhece rostos com vetores persistidos em JSON.
<code>
from flask import Flask, request, jsonify
import json, os, numpy as np
app = Flask(__name__)
ARQUIVO = "usuarios.json"
LIMIAR = 0.6
def carregar():
if not os.path.exists(ARQUIVO):
return []
with open(ARQUIVO) as f:
return json.load(f)
def salvar(nome, desc):
u = carregar()
u.append({"nome": nome, "descriptor": desc})
with open(ARQUIVO, "w") as f:
json.dump(u, f)
@app.route("/cadastrar", methods=["POST"])
def cadastrar():
data = request.json
if not data.get("nome") or not data.get("descriptor"):
return jsonify({"status":"erro"}),400
salvar(data["nome"], data["descriptor"])
return jsonify({"status":"ok"})
@app.route("/reconhecer", methods=["POST"])
def reconhecer():
data = request.json
usuarios = carregar()
for u in usuarios:
d = np.linalg.norm(np.array(data["descriptor"]) - np.array(u["descriptor"]))
if d < LIMIAR:
return jsonify({"status":"reconhecido","nome":u["nome"]})
return jsonify({"status":"nao_reconhecido"})
if __name__ == "__main__":
app.run(debug=True)
</code>
Agora crie o programa RegistroPonto.jsx
📄 RegistroPonto.jsx — reconhece o usuário e registra a presença.
<code>
import { useState, useEffect, useRef } from "react";
import * as faceapi from "face-api.js";
import { reconhecerFace } from "../services/api";
const RegistroPonto = () => {
const [status, setStatus] = useState("");
const [isRecognized, setIsRecognized] = useState(false);
const videoRef = useRef(null);
const loadModels = async () => {
const MODEL_URL = "/models";
await Promise.all([
faceapi.nets.ssdMobilenetv1.loadFromUri(MODEL_URL),
faceapi.nets.faceLandmark68Net.loadFromUri(MODEL_URL),
faceapi.nets.faceRecognitionNet.loadFromUri(MODEL_URL),
]);
};
const startVideo = async () => {
const stream = await navigator.mediaDevices.getUserMedia({ video: true });
videoRef.current.srcObject = stream;
};
const detectAndSendFace = async () => {
const detection = await faceapi
.detectSingleFace(videoRef.current)
.withFaceLandmarks()
.withFaceDescriptor();
if (detection) {
const response = await reconhecerFace(detection.descriptor);
if (response.status === "reconhecido") {
setIsRecognized(true);
setStatus(`✅ Rosto reconhecido: ${response.nome}`);
} else setStatus("❌ Rosto não reconhecido.");
}
};
useEffect(() => {
loadModels().then(startVideo);
const interval = setInterval(detectAndSendFace, 2000);
return () => clearInterval(interval);
}, []);
return (
<div>
<h2>Registro de Ponto</h2>
<video ref={videoRef} autoPlay />
<button>Registrar</button>
<p>{status}</p>
</div>
);
};
export default RegistroPonto;
</code>
Bem, pessoal, agora que todos os programas do nosso app estão prontos — o frontend com CadastroRosto.jsx e RegistroPonto.jsx, e o backend com Flask — temos uma base sólida para nosso sistema de registro de ponto com reconhecimento facial.
No próximo post, vamos explorar testes práticos, desempenho e privacidade.
Até lá, continue acompanhando — estamos construindo juntos uma solução que une IA, privacidade e web moderna.
