fix:(equipe) ajustado cadastro por regiao no acesso master

This commit is contained in:
NANDO9322 2026-02-06 11:14:55 -03:00
parent 82b597bda3
commit c5f1c40243
4 changed files with 37 additions and 12 deletions

View file

@ -282,21 +282,24 @@ func (h *Handler) Create(c *gin.Context) {
}
// Security: Only allow TargetUserID if user is ADMIN or OWNER
// Also handle Region override
userRole, _ := c.Get("role")
roleStr, _ := userRole.(string)
if input.TargetUserID != nil && *input.TargetUserID != "" {
userRole, exists := c.Get("role")
if !exists {
// Should validation fail? Or just ignore target?
// Safer to ignore target user ID if role not found
if roleStr != "SUPERADMIN" && roleStr != "BUSINESS_OWNER" {
input.TargetUserID = nil
} else {
roleStr, ok := userRole.(string)
if !ok || (roleStr != "SUPERADMIN" && roleStr != "BUSINESS_OWNER") {
input.TargetUserID = nil
}
}
}
regiao := c.GetString("regiao")
// If input has regiao and user is admin, use it
if input.Regiao != nil && *input.Regiao != "" {
if roleStr == "SUPERADMIN" || roleStr == "BUSINESS_OWNER" {
regiao = *input.Regiao
}
}
prof, err := h.service.Create(c.Request.Context(), userIDStr, input, regiao)
if err != nil {
c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})

View file

@ -47,6 +47,7 @@ type CreateProfissionalInput struct {
Email *string `json:"email"`
AvatarURL *string `json:"avatar_url"`
TargetUserID *string `json:"target_user_id"` // Optional: For admin creation
Regiao *string `json:"regiao"` // Optional: Override region
}
func (s *Service) Create(ctx context.Context, userID string, input CreateProfissionalInput, regiao string) (*generated.GetProfissionalByIDRow, error) {

View file

@ -35,11 +35,12 @@ export const ProfessionalModal: React.FC<ProfessionalModalProps> = ({
roles,
onSuccess,
}) => {
const { token: contextToken } = useAuth();
const { token: contextToken, user } = useAuth(); // Get User
const token = contextToken || "";
const initialFormState: CreateProfessionalDTO & { senha?: string; confirmarSenha?: string } = {
nome: "",
regiao: "",
funcao_profissional_id: "",
funcoes_ids: [],
email: "",
@ -87,6 +88,7 @@ export const ProfessionalModal: React.FC<ProfessionalModalProps> = ({
// Edit Mode
setFormData({
nome: professional.nome,
regiao: professional.regiao || "",
funcao_profissional_id: professional.funcao_profissional_id,
funcoes_ids: professional.functions?.map(f => f.id) || (professional.funcao_profissional_id ? [professional.funcao_profissional_id] : []),
email: professional.email || "",
@ -119,12 +121,13 @@ export const ProfessionalModal: React.FC<ProfessionalModalProps> = ({
setAvatarPreview(professional.avatar_url || (professional.avatar ?? GenericAvatar));
} else {
// Add Mode
setFormData(initialFormState);
const defaultRegion = user?.allowedRegions && user.allowedRegions.length > 0 ? user.allowedRegions[0] : "SP";
setFormData({ ...initialFormState, regiao: defaultRegion });
setAvatarPreview("");
}
setAvatarFile(null);
}
}, [isOpen, professional]);
}, [isOpen, professional]); // user dependency intentionally omitted to avoid reset loop, but safe to add if needed
// Helpers
const maskPhone = (value: string) => {
@ -387,6 +390,22 @@ export const ProfessionalModal: React.FC<ProfessionalModalProps> = ({
</div>
</div>
{/* Region Selection (Only for Multi-Region Admins) */}
{(user?.allowedRegions && user.allowedRegions.length > 1) || user?.role === "SUPERADMIN" ? (
<div className="mb-4">
<label className="block text-sm font-medium text-gray-700 mb-1">Região de Atuação *</label>
<select
value={formData.regiao || ""}
onChange={e => setFormData({ ...formData, regiao: e.target.value })}
className="block w-full rounded-md border-gray-300 shadow-sm focus:border-brand-gold focus:ring focus:ring-brand-gold focus:ring-opacity-50 p-2 border"
>
<option value="SP">São Paulo (SP)</option>
<option value="MG">Minas Gerais (MG)</option>
</select>
<p className="text-xs text-gray-500 mt-1">Selecione onde este profissional irá atuar.</p>
</div>
) : null}
{/* Seleção de Função (Movida para o topo) */}
<div className="col-span-1 md:col-span-2 mb-4">
<label className="block text-sm font-medium text-gray-700 mb-1">

View file

@ -166,6 +166,7 @@ export interface Professional {
id: string;
usuario_id?: string;
nome: string;
regiao?: string; // Add region to interface
name?: string; // Restore for compatibility
email?: string;
funcao_profissional_id: string;
@ -209,6 +210,7 @@ export interface Professional {
export interface CreateProfessionalDTO {
nome: string;
regiao?: string;
funcao_profissional_id: string; // Keep for compatibility (primary function)
funcoes_ids?: string[]; // New multi-select
email?: string;