diff --git a/src/Tables/UserMeta.php b/src/Tables/UserMeta.php new file mode 100644 index 0000000..13ede32 --- /dev/null +++ b/src/Tables/UserMeta.php @@ -0,0 +1,16 @@ +from(Database::get_table(Users::TABLE_NAME)) + ->where([Users::USER_LOGIN->value => $login]) + ->limit(1) + ->select(Users::ID->value); + + return $query->num_rows === 1 ? new static($query->fetch_assoc()[Users::ID->value]) : null; + } + + /** + * Return a User for a given email if that user exists + * + * @param string $email + * @return static|null + */ + public static function from_email(string $email): ?static { + $query = Database::current() + ->from(Database::get_table(Users::TABLE_NAME)) + ->where([Users::USER_EMAIL->value => $email]) + ->limit(1) + ->select(Users::ID->value); + + return $query->num_rows === 1 ? new static($query->fetch_assoc()[Users::ID->value]) : null; + } + + /** + * Create a new user + * + * @param string $title + * @param string $type + * @return static + */ + public static function new(string $login, string $email, ?string $display_name = null): static { + // Bail out with existing User for $login if exists + if (static::from_login($login)) { + return static::from_login($login); + } + + // Bail out with existing User for $email if exists + if (static::from_email($email)) { + return static::from_email($email); + } + + // Current auto increment value will be the id for this entity + $id = Database::current()->latest(Users::TABLE_NAME); + + $values = [ + Users::ID->value => null, + Users::USER_LOGIN->value => $login, + Users::USER_PASS->value => "", + Users::USER_NICENAME->value => slugify($login), + Users::USER_EMAIL->value => $email, + Users::USER_URL->value => "", + Users::USER_REGISTERED->value => date(static::DATETIME_FORMAT), + Users::USER_ACTIVATION_KEY->value => "", + Users::USER_STATUS->value => 0, + Users::DISPLAY_NAME->value => $display_name ?? $login + ]; + + if (!parent::create(Database::get_table(Users::TABLE_NAME), $values)) { + throw new Exception("Failed to create database entity"); + } + + return new static($id); + } + + public function __construct(public readonly int $id) { + parent::__construct( + Database::get_table(Users::TABLE_NAME), + Users::values(), + [Users::ID->value => (int) $id] + ); + } + + public string $user_login { + get => $this->get(Users::USER_LOGIN->value); + set (string $user_login) => $this->set(Users::USER_LOGIN->value, substr($user_login, 0, 60)); + } + + public string $user_pass { + get => $this->get(Users::USER_PASS->value); + set (string $user_pass) => $this->set(Users::USER_PASS->value, substr($user_pass, 0, 255)); + } + + public string $user_nicename { + get => $this->get(Users::USER_NICENAME->value); + set (string $user_nicename) => $this->set(Users::USER_NICENAME->value, substr($user_nicename, 0, 50)); + } + + public string $user_email { + get => $this->get(Users::USER_EMAIL->value); + set (string $user_email) => $this->set(Users::USER_EMAIL->value, substr($user_email, 0, 100)); + } + + public string $user_url { + get => $this->get(Users::USER_URL->value); + set (string $user_url) => $this->set(Users::USER_URL->value, substr($user_url, 0, 100)); + } + + public DateTimeImmutable $user_registered { + get => new DateTimeImmutable($this->get(Users::USER_REGISTERED->value)); + set (DateTimeImmutable $user_registered) => $this->set(Users::USER_REGISTERED->value, $user_registered->format(static::DATETIME_FORMAT), $user_registered); + } + + public string $user_activation_key { + get => $this->get(Users::USER_ACTIVATION_KEY->value); + set (string $user_activation_key) => $this->set(Users::USER_ACTIVATION_KEY->value, substr($user_activation_key, 0, 255)); + } + + public int $user_status { + get => $this->get(Users::USER_STATUS->value); + set (int $user_status) => $this->set(Users::USER_STATUS->value, $user_status); + } + + public string $display_name { + get => $this->get(Users::DISPLAY_NAME->value); + set (string $display_name) => $this->set(Users::DISPLAY_NAME->value, substr($display_name, 0, 250)); + } + + /** + * Set the password for this User + * + * @param string $password + * @return void + */ + public function set_password(string $password): void { + $this->user_pass = password_hash($password, PASSWORD_DEFAULT); + } + + /** + * Check if the password for this User is $password + * + * @param string $password + * @return bool + */ + public function validate_password(string $password): bool { + return password_verify($password, $this->user_pass); + } + } diff --git a/src/Users/UserMeta.php b/src/Users/UserMeta.php new file mode 100644 index 0000000..322d262 --- /dev/null +++ b/src/Users/UserMeta.php @@ -0,0 +1,98 @@ +from(Database::get_table(UserMetaTable::TABLE_NAME)) + ->where([ + UserMetaTable::USER_ID->value => $user->id, + UserMetaTable::META_KEY->value => $key + ]) + ->limit(1) + ->select(UserMetaTable::UMETA_ID->value); + + return $query->num_rows === 1 ? new static($query->fetch_assoc()[UserMetaTable::UMETA_ID->value]) : false; + } + + /** + * Get all user meta entries for a given User + * + * @param string $name + * @return array + */ + public static function get_all_user_meta(User $user): array { + $query = Database::current() + ->from(Database::get_table(UserMetaTable::TABLE_NAME)) + ->where([UserMetaTable::USER_ID->value => $user->id]) + ->select(UserMetaTable::UMETA_ID->value); + + return array_map(fn(array $post_meta): static => new static($post_meta[UserMetaTable::UMETA_ID->value]), $query->fetch_all(MYSQLI_ASSOC)); + } + + /** + * Create a new user + * + * @param string $title + * @param string $type + * @return static + */ + public static function new(User $user, ?string $meta_key = null, ?string $meta_value = null): static { + // Current auto increment value will be the id for this entity + $id = Database::current()->latest(UserMetaTable::TABLE_NAME); + + $values = [ + UserMetaTable::UMETA_ID->value => null, + UserMetaTable::USER_ID->value => $user->id, + UserMetaTable::META_KEY->value => $meta_key, + UserMetaTable::META_VALUE->value => $meta_value + ]; + + if (!parent::create(Database::get_table(UserMetaTable::TABLE_NAME), $values)) { + throw new Exception("Failed to create database entity"); + } + + return new static($id); + } + + public function __construct(public readonly int $id) { + parent::__construct( + Database::get_table(UserMetaTable::TABLE_NAME), + UserMetaTable::values(), + [UserMetaTable::UMETA_ID->value => (int) $id] + ); + } + + public User $user { + get => new User($this->get(UserMetaTable::USER_ID->value)); + set (User $user) => $this->set(UserMetaTable::USER_ID->value, $user->id, $user); + } + + public string $meta_key { + get => $this->get(UserMetaTable::META_KEY->value); + set (string $meta_key) => $this->set(UserMetaTable::META_KEY->value, substr($meta_key, 0, 255)); + } + + public string $meta_value { + get => $this->get(UserMetaTable::META_VALUE->value); + set (string $meta_value) => $this->set(UserMetaTable::META_VALUE->value, $meta_value); + } + }