src/Cms/CoreBundle/Entity/OneRoster/OneRosterUser.php line 20

Open in your IDE?
  1. <?php
  2. namespace Cms\CoreBundle\Entity\OneRoster;
  3. use Cms\CoreBundle\Entity\AbstractOneRosterEntity;
  4. use Doctrine\ORM\Mapping as ORM;
  5. use Reinder83\BinaryFlags\Bits;
  6. /**
  7.  * @see https://www.imsglobal.org/oneroster-v11-final-specification#_Toc480452019
  8.  *
  9.  * Class OneRosterUser
  10.  * @package Cms\CoreBundle\Entity\OneRoster
  11.  *
  12.  * @ORM\Entity(
  13.  *     repositoryClass = "Cms\CoreBundle\Doctrine\OneRoster\OneRosterUserRepository"
  14.  * )
  15.  */
  16. class OneRosterUser extends AbstractOneRosterEntity
  17. {
  18.     const ONEROSTER_TYPE 'user';
  19.     const DISCR 'User';
  20.     const ROLES_MAPPING = [
  21.         // staff
  22.         self::ENUMS__ROLE_TYPE__ADMINISTRATOR => self::TYPES__STAFF,
  23.         self::ENUMS__ROLE_TYPE__AIDE => self::TYPES__STAFF,
  24.         self::ENUMS__ROLE_TYPE__PROCTOR => self::TYPES__STAFF,
  25.         self::ENUMS__ROLE_TYPE__TEACHER => self::TYPES__STAFF,
  26.         // custom
  27.         self::ENUMS__ROLE_TYPE__STAFF => self::TYPES__STAFF,
  28.         self::ENUMS__ROLE_TYPE__COMMUNITY => self::TYPES__COMMUNITY,
  29.         // family
  30.         self::ENUMS__ROLE_TYPE__GUARDIAN => self::TYPES__FAMILY,
  31.         self::ENUMS__ROLE_TYPE__PARENT => self::TYPES__FAMILY,
  32.         self::ENUMS__ROLE_TYPE__RELATIVE => self::TYPES__FAMILY,
  33.         // student
  34.         self::ENUMS__ROLE_TYPE__STUDENT => self::TYPES__STUDENT,
  35.     ];
  36.     const TYPES_MAPPING = [
  37.         self::TYPES__STAFF => [
  38.             self::ENUMS__ROLE_TYPE__ADMINISTRATOR,
  39.             self::ENUMS__ROLE_TYPE__AIDE,
  40.             self::ENUMS__ROLE_TYPE__PROCTOR,
  41.             self::ENUMS__ROLE_TYPE__TEACHER,
  42.             // custom
  43.             self::ENUMS__ROLE_TYPE__STAFF,
  44.         ],
  45.         self::TYPES__FAMILY => [
  46.             self::ENUMS__ROLE_TYPE__GUARDIAN,
  47.             self::ENUMS__ROLE_TYPE__PARENT,
  48.             self::ENUMS__ROLE_TYPE__RELATIVE,
  49.         ],
  50.         self::TYPES__STUDENT => [
  51.             self::ENUMS__ROLE_TYPE__STUDENT,
  52.         ],
  53.         self::TYPES__COMMUNITY => [
  54.             self::ENUMS__ROLE_TYPE__COMMUNITY,
  55.         ],
  56.     ];
  57.     const TYPES = [
  58.         'staff' => self::TYPES__STAFF,
  59.         'family' => self::TYPES__FAMILY,
  60.         'student' => self::TYPES__STUDENT,
  61.         'community' => self::TYPES__COMMUNITY,
  62.     ];
  63.     const TYPES_LOOKUP = [
  64.         self::TYPES__STAFF => 'staff',
  65.         self::TYPES__FAMILY => 'family',
  66.         self::TYPES__STUDENT => 'student',
  67.         self::TYPES__COMMUNITY => 'community',
  68.     ];
  69.     const TYPES__STAFF Bits::BIT_1;
  70.     const TYPES__FAMILY Bits::BIT_2;
  71.     const TYPES__STUDENT Bits::BIT_3;
  72.     const TYPES__COMMUNITY Bits::BIT_4;
  73.     /**
  74.      * @var string|null
  75.      *
  76.      * @ORM\Column(
  77.      *     type = "string",
  78.      *     nullable = false,
  79.      * )
  80.      */
  81.     protected ?string $username null;
  82.     /**
  83.      * @var array|array[]
  84.      *
  85.      * @ORM\Column(
  86.      *     type = "json",
  87.      *     nullable = false,
  88.      * )
  89.      */
  90.     protected array $userIds = [];
  91.     /**
  92.      * @var bool
  93.      *
  94.      * @ORM\Column(
  95.      *     type = "boolean",
  96.      *     nullable = false,
  97.      *     options = {
  98.      *         "default" = false,
  99.      *     },
  100.      * )
  101.      */
  102.     protected bool $enabledUser false;
  103.     /**
  104.      * @var string|null
  105.      *
  106.      * @ORM\Column(
  107.      *     type = "string",
  108.      *     nullable = false,
  109.      * )
  110.      */
  111.     protected ?string $givenName null;
  112.     /**
  113.      * @var string|null
  114.      *
  115.      * @ORM\Column(
  116.      *     type = "string",
  117.      *     nullable = false,
  118.      * )
  119.      */
  120.     protected ?string $familyName null;
  121.     /**
  122.      * @var string|null
  123.      *
  124.      * @ORM\Column(
  125.      *     type = "string",
  126.      *     nullable = true,
  127.      * )
  128.      */
  129.     protected ?string $middleName null;
  130.     /**
  131.      * @see https://www.imsglobal.org/oneroster-v11-final-specification#_Toc480452025
  132.      *
  133.      * @var string|null
  134.      *
  135.      * @ORM\Column(
  136.      *     type = "string",
  137.      *     nullable = false,
  138.      * )
  139.      */
  140.     protected ?string $role null;
  141.     /**
  142.      * @var string|null
  143.      *
  144.      * @ORM\Column(
  145.      *     type = "string",
  146.      *     nullable = true,
  147.      * )
  148.      */
  149.     protected ?string $identifier null;
  150.     /**
  151.      * @var string|null
  152.      *
  153.      * @ORM\Column(
  154.      *     type = "string",
  155.      *     nullable = true,
  156.      * )
  157.      */
  158.     protected ?string $email null;
  159.     /**
  160.      * @var string|null
  161.      *
  162.      * @ORM\Column(
  163.      *     type = "string",
  164.      *     nullable = true,
  165.      * )
  166.      */
  167.     protected ?string $sms null;
  168.     /**
  169.      * @var string|null
  170.      *
  171.      * @ORM\Column(
  172.      *     type = "string",
  173.      *     nullable = true,
  174.      * )
  175.      */
  176.     protected ?string $phone null;
  177.     /**
  178.      * @var array|array[]
  179.      *
  180.      * @ORM\Column(
  181.      *     type = "json",
  182.      *     nullable = false,
  183.      * )
  184.      */
  185.     protected array $agents = [];
  186.     /**
  187.      * @var array|array[]
  188.      *
  189.      * @ORM\Column(
  190.      *     type = "json",
  191.      *     nullable = false,
  192.      * )
  193.      */
  194.     protected array $orgs = [];
  195.     /**
  196.      * TODO: should this be nullable?
  197.      *
  198.      * @see https://ceds.ed.gov/CEDSElementDetails.aspx?TermId=7100
  199.      *
  200.      * @var array|string[]
  201.      *
  202.      * @ORM\Column(
  203.      *     type = "json",
  204.      *     nullable = false,
  205.      * )
  206.      */
  207.     protected array $grades = [];
  208.     /**
  209.      * @return string|null
  210.      */
  211.     public function getUsername(): ?string
  212.     {
  213.         return $this->username;
  214.     }
  215.     /**
  216.      * @param string $value
  217.      * @return $this
  218.      */
  219.     public function setUsername(string $value): self
  220.     {
  221.         $this->username $value;
  222.         return $this;
  223.     }
  224.     /**
  225.      * @return array|array[]
  226.      */
  227.     public function getUserIds(): array
  228.     {
  229.         return $this->userIds;
  230.     }
  231.     /**
  232.      * @param array|array[] $value
  233.      * @return $this
  234.      */
  235.     public function setUserIds(array $value): self
  236.     {
  237.         $this->userIds $this->parseArray(
  238.             $value,
  239.             function (array $a, array $b) {
  240.                 $result strcmp($a['type'], $b['type']);
  241.                 if ($result === 0) {
  242.                     $result strcmp($a['identifier'], $b['identifier']);
  243.                 }
  244.                 return $result;
  245.             }
  246.         );
  247.         return $this;
  248.     }
  249.     /**
  250.      * @return bool
  251.      */
  252.     public function isEnabledUser(): bool
  253.     {
  254.         return $this->enabledUser;
  255.     }
  256.     /**
  257.      * @param bool $value
  258.      * @return $this
  259.      */
  260.     public function setEnabledUser(bool $value): self
  261.     {
  262.         $this->enabledUser $value;
  263.         return $this;
  264.     }
  265.     /**
  266.      * NOTE: this is NOT a OneRoster data point
  267.      * This is an internal helper method to easier determine if the record should be usable in the system or not.
  268.      * Usable records are both "active" (base OneRoster status) and set as and "enabled user".
  269.      *
  270.      * @return bool
  271.      */
  272.     public function isUsable(): bool
  273.     {
  274.         return ($this->isStatusActive() && $this->isEnabledUser());
  275.     }
  276.     /**
  277.      * TODO: hijacked this to allow nulls, by one roster rules this is not allowed, but gg4l data seems to allow it...
  278.      *
  279.      * @return string|null
  280.      */
  281.     public function getGivenName(): ?string
  282.     {
  283.         return $this->givenName;
  284.     }
  285.     /**
  286.      * TODO: hijacked this to allow nulls, by one roster rules this is not allowed, but gg4l data seems to allow it...
  287.      *
  288.      * @param string|null $value
  289.      * @return $this
  290.      */
  291.     public function setGivenName(?string $value): self
  292.     {
  293.         $this->givenName trim($value) ?: null;
  294.         return $this;
  295.     }
  296.     /**
  297.      * TODO: hijacked this to allow nulls, by one roster rules this is not allowed, but gg4l data seems to allow it...
  298.      *
  299.      * @return string|null
  300.      */
  301.     public function getFamilyName(): ?string
  302.     {
  303.         return $this->familyName;
  304.     }
  305.     /**
  306.      * TODO: hijacked this to allow nulls, by one roster rules this is not allowed, but gg4l data seems to allow it...
  307.      *
  308.      * @param string|null $value
  309.      * @return $this
  310.      */
  311.     public function setFamilyName(?string $value): self
  312.     {
  313.         $this->familyName trim($value) ?: null;
  314.         return $this;
  315.     }
  316.     /**
  317.      * @return string|null
  318.      */
  319.     public function getMiddleName(): ?string
  320.     {
  321.         return $this->middleName;
  322.     }
  323.     /**
  324.      * @param string|null $value
  325.      * @return $this
  326.      */
  327.     public function setMiddleName(?string $value): self
  328.     {
  329.         $this->middleName trim($value) ?: null;
  330.         return $this;
  331.     }
  332.     /**
  333.      * @return string|null
  334.      */
  335.     public function getRole(): ?string
  336.     {
  337.         return $this->role;
  338.     }
  339.     /**
  340.      * @param string $value
  341.      * @return $this
  342.      */
  343.     public function setRole(string $value): self
  344.     {
  345.         $this->role $value;
  346.         return $this;
  347.     }
  348.     /**
  349.      * @return int|null
  350.      */
  351.     public function getRoleType(): ?int
  352.     {
  353.         return ($this->getRole()) ? self::ROLES_MAPPING[$this->getRole()] : null;
  354.     }
  355.     /**
  356.      * @return string|null
  357.      */
  358.     public function getRoleTypeName(): ?string
  359.     {
  360.         return ($this->getRoleType()) ? self::TYPES_LOOKUP[$this->getRoleType()] : null;
  361.     }
  362.     /**
  363.      * @param int $type
  364.      * @return bool
  365.      */
  366.     public function isRoleType(int $type): bool
  367.     {
  368.         return ($this->getRoleType() === $type);
  369.     }
  370.     /**
  371.      * TODO: rename and fix code...
  372.      *
  373.      * @return bool
  374.      */
  375.     public function isRoleStaff(): bool
  376.     {
  377.         return $this->isRoleType(self::TYPES__STAFF);
  378.     }
  379.     /**
  380.      * TODO: rename and fix code...
  381.      *
  382.      * @return bool
  383.      */
  384.     public function isRoleStudent(): bool
  385.     {
  386.         return $this->isRoleType(self::TYPES__STUDENT);
  387.     }
  388.     /**
  389.      * TODO: rename and fix code...
  390.      *
  391.      * @return bool
  392.      */
  393.     public function isRoleCommunity(): bool
  394.     {
  395.         return $this->isRoleType(self::TYPES__COMMUNITY);
  396.     }
  397.     /**
  398.      * TODO: rename and fix code...
  399.      *
  400.      * @return bool
  401.      */
  402.     public function isRoleFamily(): bool
  403.     {
  404.         return $this->isRoleType(self::TYPES__FAMILY);
  405.     }
  406.     /**
  407.      * @return string|null
  408.      */
  409.     public function getIdentifier(): ?string
  410.     {
  411.         return $this->identifier;
  412.     }
  413.     /**
  414.      * @param string|null $value
  415.      * @return $this
  416.      */
  417.     public function setIdentifier(?string $value): self
  418.     {
  419.         $this->identifier trim($value) ?: null;
  420.         return $this;
  421.     }
  422.     /**
  423.      * @param string $type
  424.      * @return array|string[]
  425.      */
  426.     public function getContacts(string $type): array
  427.     {
  428.         $func sprintf(
  429.             'get%sContacts',
  430.             ucfirst($type)
  431.         );
  432.         if ( ! method_exists($this$func)) {
  433.             throw new \Exception();
  434.         }
  435.         return call_user_func([$this$func]);
  436.     }
  437.     /**
  438.      * @return string|null
  439.      */
  440.     public function getEmail(): ?string
  441.     {
  442.         return strtolower(trim($this->email)) ?: null;
  443.     }
  444.     /**
  445.      * @param string|null $value
  446.      * @return $this
  447.      */
  448.     public function setEmail(?string $value): self
  449.     {
  450.         $this->email strtolower(trim($value)) ?: null;
  451.         return $this;
  452.     }
  453.     /**
  454.      * @return array|string[]
  455.      */
  456.     public function getEmailContacts(): array
  457.     {
  458.         $values array_values(array_filter([
  459.             $this->getEmail(),
  460.         ]));
  461.         sort($values);
  462.         return $values;
  463.     }
  464.     /**
  465.      * @return string|null
  466.      */
  467.     public function getSms(): ?string
  468.     {
  469.         return trim($this->sms) ?: null;
  470.     }
  471.     /**
  472.      * @param string|null $value
  473.      * @return $this
  474.      */
  475.     public function setSms(?string $value): self
  476.     {
  477.         $this->sms trim($value) ?: null;
  478.         return $this;
  479.     }
  480.     /**
  481.      * @return array|string[]
  482.      */
  483.     public function getSmsContacts(): array
  484.     {
  485.         $values array_values(array_filter([
  486.             $this->getSms(),
  487.         ]));
  488.         sort($values);
  489.         return $values;
  490.     }
  491.     /**
  492.      * @return string|null
  493.      */
  494.     public function getPhone(): ?string
  495.     {
  496.         return trim($this->phone) ?: null;
  497.     }
  498.     /**
  499.      * @param string|null $value
  500.      * @return $this
  501.      */
  502.     public function setPhone(?string $value): self
  503.     {
  504.         $this->phone trim($value) ?: null;
  505.         return $this;
  506.     }
  507.     /**
  508.      * @return array|string[]
  509.      */
  510.     public function getVoiceContacts(): array
  511.     {
  512.         $values array_values(array_filter([
  513.             $this->getPhone(),
  514.         ]));
  515.         sort($values);
  516.         return $values;
  517.     }
  518.     /**
  519.      * @return array|array[]
  520.      */
  521.     public function getAgents(): array
  522.     {
  523.         return $this->agents;
  524.     }
  525.     /**
  526.      * @param array|array[] $value
  527.      * @return $this
  528.      */
  529.     public function setAgents(array $value): self
  530.     {
  531.         $this->agents $this->parseGuidRefs($value);
  532.         return $this;
  533.     }
  534.     /**
  535.      * @return array<string>
  536.      */
  537.     public function getAgentsSourcedIds(): array
  538.     {
  539.         return array_values(array_filter(array_unique(array_map(
  540.             static function (array $agent) {
  541.                 return $agent['sourcedId'];
  542.             },
  543.             $this->getAgents(),
  544.         ))));
  545.     }
  546.     /**
  547.      * @return array|array[]
  548.      */
  549.     public function getOrgs(): array
  550.     {
  551.         // TODO: is this hack needed?
  552.         if ($this->orgs && is_string($this->orgs[0])) {
  553.             return array_map(
  554.                 static function (string $sourcedId) {
  555.                     return [
  556.                         'type' => 'org',
  557.                         'sourcedId' => $sourcedId,
  558.                     ];
  559.                 },
  560.                 $this->orgs
  561.             );
  562.         }
  563.         return $this->orgs;
  564.     }
  565.     /**
  566.      * @return array<string>
  567.      */
  568.     public function getOrgsSourcedIds(): array
  569.     {
  570.         return array_values(array_filter(array_unique(array_map(
  571.             static function (array $org) {
  572.                 return $org['sourcedId'];
  573.             },
  574.             $this->getOrgs(),
  575.         ))));
  576.     }
  577.     /**
  578.      * @param array|array[] $value
  579.      * @return $this
  580.      */
  581.     public function setOrgs(array $value): self
  582.     {
  583.         $this->orgs $this->parseGuidRefs($value);
  584.         return $this;
  585.     }
  586.     /**
  587.      * @return array|string[]
  588.      */
  589.     public function getGrades(): array
  590.     {
  591.         return $this->grades;
  592.     }
  593.     /**
  594.      * @param array|string[] $value
  595.      * @return $this
  596.      */
  597.     public function setGrades(array $value): OneRosterUser
  598.     {
  599.         $this->grades $this->parseArray($value);
  600.         return $this;
  601.     }
  602. }