Je ne sais pas pourquoi mais je frappe un mur absolu en essayant de trouver cette déclaration sélective. Il y a peut-être une fonction PHP / MYSQL que je ne connais pas qui pourrait aider. L'idée est simple pour ce logiciel de gestion des utilisateurs: il y a des managers, et les managers peuvent (mais ne doivent pas) partager des clients. Parmi le manager et la relation client partagée, l'un des managers peut être désigné comme lead. Voici donc à quoi ressemble l'exemple de base de la base de données pour 1 client partagé entre 2 gestionnaires et affecté, et un autre client également partagé mais NON affecté (représenté par zéro).

DROP TABLE IF EXISTS clients;

CREATE TABLE clients
(client_id SERIAL PRIMARY KEY
,client_name VARCHAR(12) UNIQUE
);

INSERT INTO clients VALUES
(555,'Jimmy'), 
(789,'Tyler'); 

DROP TABLE IF EXISTS managers;

CREATE TABLE managers
(manager_id SERIAL PRIMARY KEY
,manager_name VARCHAR(12)UNIQUE
);

INSERT INTO managers VALUES
(123,'Michael'),
(456,'David');

DROP TABLE IF EXISTS relationships;

CREATE TABLE relationships
(client_id INT NOT NULL
,manager_id INT NOT NULL
,assigned INT NOT NULL
,PRIMARY KEY(client_id,manager_id)
);

INSERT INTO relationships VALUES
(555, 123, 0),
(555, 456, 1),
(789, 123, 0),
(789, 456, 0);

Pour en venir au fait: la déclaration que j'essaie de faire est de montrer à un manager tous les clients avec lesquels il a une relation, mais qui ne sont PAS affectés à lui ou à quelqu'un d'autre de son équipe, c'est-à-dire sélectionner tous mes clients où personne n'est désigné comme chef de file.

Entrée attendue: affichez tous les clients avec lesquels le gestionnaire 123 a une relation, mais n'a encore été attribué à aucun gestionnaire. Résultat attendu: client 789

Heureux de clarifier car je peux voir que cela est ouvertement déroutant comme décrit.

0
bartha19 4 nov. 2019 à 16:21

2 réponses

SELECT c.* 
  FROM managers m 
  JOIN relationships r 
    ON r.manager_id = m.manager_id 
  JOIN clients c 
    ON c.client_id = r.client_id 
  LEFT 
  JOIN relationships x 
    ON x.client_id = c.client_id 
   AND x.assigned = 1 
 WHERE m.manager_id = 123 
   AND r.assigned = 0 
   AND x.client_id IS NULL;
+-----------+-------------+
| client_id | client_name |
+-----------+-------------+
|       789 | Tyler       |
+-----------+-------------+
0
Strawberry 4 nov. 2019 à 18:15

Vous devrez donc commencer par trouver tous les identifiants client du gestionnaire dans RELATIONS, mais supprimez tous ceux qui ont déjà un gestionnaire affecté.

Selon la taille de la table, vous voudrez peut-être réécrire cela, mais voici une approche:

1) Obtenez tous les clients qui n'ont pas de gestionnaire:

SELECT R1.client_id, SUM(R1.assigned) as sumassigned FROM relationships AS R1 GROUP BY R1.client_id HAVING ( SUM(R1.assigned) = 0)

Maintenant, c'est plus facile, il vous suffit de rejoindre, par exemple:

SELECT R2.client_id, R2.manager_id FROM relationships AS R2
INNER JOIN 
(SELECT R1.client_id, SUM(R1.assigned) as sumassigned FROM relationships AS R1 GROUP BY R1.client_id HAVING ( SUM(R1.assigned) = 0) ) AS DRVNOMANAGER
ON (R2.client_id = DRVNOMANAGER.client_id)
WHERE (R2.manager_id = 123)

Non testé. (ce qui signifie que vous devrez peut-être le réparer)

L'idée est de créer une table dérivée (temporaire) contenant tous les clients sans gestionnaire, puis de faire une jointure interne sur votre question d'origine ("quels clients ce gestionnaire 123 sait-il qui n'en a pas d'autre assigné)

Est-ce que cela résout votre problème?

PS: De telles choses sont beaucoup plus faciles à résoudre en PHP, mais si votre jeu de données est énorme, ce n'est pas faisable.

OP a demandé des noms de clients, il suffit donc d'ajouter que:

        SELECT R2.client_id, R2.manager_id, C.client_name  FROM relationships AS R2
INNER JOIN 
        (SELECT R1.client_id, SUM(R1.assigned) as sumassigned FROM relationships
 AS R1 GROUP BY R1.client_id HAVING ( SUM(R1.assigned) = 0) ) AS DRVNOMANAGER
        ON (R2.client_id = DRVNOMANAGER.client_id)
    INNER JOIN clients AS C ON (C.client_id = R2.client_id)
        WHERE (R2.manager_id = 123)

==============================================

C'ÉTAIT MA VIEILLE RÉPONSE. PLUS PERTINENT.

"sélectionner tous mes clients où personne n'est désigné comme chef de file."

Si je vous lis bien, cela signifie: Obtenez tous les ID client à partir de RELATIONS où un ID gestionnaire est donné, ET affecté = 0. (assigné = 0 signifiant "personne n'est assigné comme chef de file.")

Est-ce exact?

Ensuite, vous vous retrouvez avec quelque chose comme ça (pour managerid 123):

SELECT R.clientid, C.clientname FROM RELATIONSHIPS AS R WHERE ( (R.managerid = 123) AND (R.assigned=0))
INNER JOIN CLIENTS AS C ON (C.clientid = R.clientid)

J'ai supprimé les espaces dans les noms de colonnes car je déteste les espaces dans les noms de colonnes.

0
Erwin Moller 4 nov. 2019 à 20:13