state = $this->state ?: \md5(\uniqid(Contracts\RFC6749_ABNF_STATE, true)); return $this->buildAuthUrlFromBase('https://access.line.me/oauth2/'.$this->version.'/authorize'); } protected function getTokenUrl(): string { return $this->baseUrl.$this->version.'/token'; } #[ArrayShape([ Contracts\RFC6749_ABNF_CLIENT_ID => 'null|string', Contracts\RFC6749_ABNF_CLIENT_SECRET => 'null|string', Contracts\RFC6749_ABNF_CODE => 'string', Contracts\RFC6749_ABNF_REDIRECT_URI => 'null|string', Contracts\RFC6749_ABNF_GRANT_TYPE => 'string', ])] protected function getTokenFields(string $code): array { return parent::getTokenFields($code) + [Contracts\RFC6749_ABNF_GRANT_TYPE => Contracts\RFC6749_ABNF_AUTHORATION_CODE]; } protected function getUserByToken(string $token): array { $response = $this->getHttpClient()->get( 'https://api.line.me/v2/profile', [ 'headers' => [ 'Accept' => 'application/json', 'Authorization' => 'Bearer '.$token, ], ] ); return $this->fromJsonBody($response); } #[Pure] protected function mapUserToObject(array $user): Contracts\UserInterface { return new User([ Contracts\ABNF_ID => $user['userId'] ?? null, Contracts\ABNF_NAME => $user['displayName'] ?? null, Contracts\ABNF_NICKNAME => $user['displayName'] ?? null, Contracts\ABNF_AVATAR => $user['pictureUrl'] ?? null, Contracts\ABNF_EMAIL => null, ]); } }