Merge branch '0.7.x' of github.com:appwrite/appwrite into swoole-and-functions
This commit is contained in:
commit
99c10508e5
31
CHANGES.md
31
CHANGES.md
|
@ -3,14 +3,30 @@
|
|||
## Features
|
||||
|
||||
- New route in Locale API to fetch a list of languages (@TorstenDittmann)
|
||||
- Improved Webhooks and New System Events - [Learn more]()
|
||||
- Added Google Fonts to Appwrite for offline availability
|
||||
- Added response to /locale/languages API with a list of languages (@TorstenDittmann ,[#351](https://github.com/appwrite/appwrite/issues/351))
|
||||
- Added API response payload structure info and examples to the docs site ([#381](https://github.com/appwrite/appwrite/issues/381))
|
||||
- Added Google Fonts to Appwrite for offline availability
|
||||
- Added a new route in the Avatars API to get user initials avatar ([#386](https://github.com/appwrite/appwrite/issues/386))
|
||||
- Added option to delete team from the console ([#380](https://github.com/appwrite/appwrite/issues/380))
|
||||
- Added option to view team members from the console ([#378](https://github.com/appwrite/appwrite/issues/378))
|
||||
- Add option to assign new team members to a team from the console and the API ([#379](https://github.com/appwrite/appwrite/issues/379))
|
||||
- Added support for Brotli compression (@PedroCisnerosSantana, @Rohitub222, [#310](https://github.com/appwrite/appwrite/issues/310))
|
||||
- Added a new route in the Avatars API to get user initials avatar
|
||||
- Added option to delete team from the console
|
||||
- Added Select All Checkbox for on Console API key Scopes Screen ([#477](https://github.com/appwrite/appwrite/issues/477))
|
||||
- Added pagination and search for team memberships route ([#387](https://github.com/appwrite/appwrite/issues/387))
|
||||
- UI performance & accessibility improvements ([#406](https://github.com/appwrite/appwrite/pull/406))
|
||||
- Added option to view team members from the console
|
||||
- Added option to join a user to any team from the console
|
||||
- Added option to delete user from the API (@TorstenDittmann - #378)
|
||||
- Added option to delete user from the console (@PineappleIOnic - #538)
|
||||
- Added support for Brotli compression (@PedroCisnerosSantana, @Rohitub222)
|
||||
- Created lazy deletion of data worker ([#521](https://github.com/appwrite/appwrite/issues/521))
|
||||
- All emails are now sent asynchronously for improved performance (@TorstenDittmann ,[#402](https://github.com/appwrite/appwrite/pull/402))
|
||||
- Updated grid for OAuth2 providers list in the console ([#413](https://github.com/appwrite/appwrite/issues/413))
|
||||
- Upgraded Redis Resque queue library to version 1.3.6 ([#319](https://github.com/appwrite/appwrite/issues/319))
|
||||
- Moved all Appwrite container logs to STDOUT & STDERR ([#389](https://github.com/appwrite/appwrite/issues/389))
|
||||
- New UI micro-interactions and CSS fixes (@AnatoleLucet)
|
||||
- UI performance & accessibility improvements (#406)
|
||||
- New Doctor CLI to debug the Appwrite server ([#415](https://github.com/appwrite/appwrite/issues/415))
|
||||
|
@ -43,6 +59,8 @@
|
|||
- Upgraded Traefik image to version 2.3
|
||||
- Upgraded Redis Docker image to version 6.0 (alpine)
|
||||
- Upgraded Influxdb Docker image to version 1.8 (alpine)
|
||||
- Added option to disable mail sending by setting empty SMTP host
|
||||
- Upgraded installation script ([#490](https://github.com/appwrite/appwrite/issues/490))
|
||||
|
||||
## Breaking Changes (Read before upgrading!)
|
||||
- **Deprecated** `first` and `last` query params for documents list route in the database API
|
||||
|
@ -54,6 +72,17 @@
|
|||
|
||||
## Bug Fixes
|
||||
|
||||
- Fixed an issue where Special characters in _APP_OPENSSL_KEY_V1_ env caused an error ([#732](https://github.com/appwrite/appwrite/issues/732))
|
||||
- Fixed an issue where Account webhook doesn't trigger through the console ([#493](https://github.com/appwrite/appwrite/issues/493))
|
||||
- Fixed case sensitive country flag code ([#526](https://github.com/appwrite/appwrite/issues/526))
|
||||
- Fixed redirect to Appwrite login page when deep link is provided ([#427](https://github.com/appwrite/appwrite/issues/427))
|
||||
- Fixed an issue where Creating documents fails for parent documents would result in an error ([#514](https://github.com/appwrite/appwrite/issues/514))
|
||||
- Fixed an issue with Email Sending Problem using external smtp ([#707](https://github.com/appwrite/appwrite/issues/707))
|
||||
- Fixed an issue where you could not remove a key from User Prefs ([#316](https://github.com/appwrite/appwrite/issues/316))
|
||||
- Fixed an issue where events are not fully visible in the console ([#492](https://github.com/appwrite/appwrite/issues/492))
|
||||
- Fixed an issue where UI would wrongly validate integers ([#394](https://github.com/appwrite/appwrite/issues/394))
|
||||
- Fixed an issue where graphs were cut in mobile view ([#376](https://github.com/appwrite/appwrite/issues/376))
|
||||
- Fixed URL issue where console/ would not display list of projects ([#372](https://github.com/appwrite/appwrite/issues/372))
|
||||
- Fixed output of /v1/health/queue/certificates returning wrong data
|
||||
- Fixed bug where team members count was wrong in some cases
|
||||
- Fixed network calculation for uploaded files
|
||||
|
|
|
@ -15,7 +15,7 @@ RUN composer update --ignore-platform-reqs --optimize-autoloader \
|
|||
FROM php:7.4-cli-alpine as step1
|
||||
|
||||
ENV PHP_REDIS_VERSION=5.3.0 \
|
||||
PHP_SWOOLE_VERSION=v4.5.6 \
|
||||
PHP_SWOOLE_VERSION=v4.5.8 \
|
||||
PHP_MAXMINDDB_VERSION=v1.8.0 \
|
||||
PHP_XDEBUG_VERSION=sdebug_2_9-beta
|
||||
|
||||
|
|
|
@ -300,6 +300,15 @@ $collections = [
|
|||
'name' => 'Token',
|
||||
'structure' => true,
|
||||
'rules' => [
|
||||
[
|
||||
'$collection' => Database::SYSTEM_COLLECTION_RULES,
|
||||
'label' => 'User ID',
|
||||
'key' => 'userId',
|
||||
'type' => Database::SYSTEM_VAR_TYPE_TEXT,
|
||||
'default' => null,
|
||||
'required' => false,
|
||||
'array' => false,
|
||||
],
|
||||
[
|
||||
'$collection' => Database::SYSTEM_COLLECTION_RULES,
|
||||
'label' => 'Type',
|
||||
|
|
|
@ -19,6 +19,18 @@ return [
|
|||
'account.update.prefs' => [
|
||||
'description' => 'This event triggers when the account preferences are updated.',
|
||||
],
|
||||
'account.recovery.create' => [
|
||||
'description' => 'This event triggers when the account recovery token is created.',
|
||||
],
|
||||
'account.recovery.update' => [
|
||||
'description' => 'This event triggers when the account recovery token is validated.',
|
||||
],
|
||||
'account.verification.create' => [
|
||||
'description' => 'This event triggers when the account verification token is created.',
|
||||
],
|
||||
'account.verification.update' => [
|
||||
'description' => 'This event triggers when the account verification token is validated.',
|
||||
],
|
||||
'account.delete' => [
|
||||
'description' => 'This event triggers when the account is deleted.',
|
||||
],
|
||||
|
@ -40,8 +52,8 @@ return [
|
|||
'database.documents.create' => [
|
||||
'description' => 'This event triggers when a database document is created.',
|
||||
],
|
||||
'database.documents.patch' => [
|
||||
'description' => 'This event triggers when a database document is patched.',
|
||||
'database.documents.update' => [
|
||||
'description' => 'This event triggers when a database document is updated.',
|
||||
],
|
||||
'database.documents.delete' => [
|
||||
'description' => 'This event triggers when a database document is deleted.',
|
||||
|
@ -67,4 +79,22 @@ return [
|
|||
'users.sessions.delete' => [
|
||||
'description' => 'This event triggers when a user session is deleted from users API.',
|
||||
],
|
||||
'teams.create' => [
|
||||
'description' => 'This event triggers when a team is created.',
|
||||
],
|
||||
'teams.update' => [
|
||||
'description' => 'This event triggers when a team is updated.',
|
||||
],
|
||||
'teams.delete' => [
|
||||
'description' => 'This event triggers when a team is deleted.',
|
||||
],
|
||||
'teams.memberships.create' => [
|
||||
'description' => 'This event triggers when a team memberships is created.',
|
||||
],
|
||||
'teams.memberships.update.status' => [
|
||||
'description' => 'This event triggers when a team memberships status is updated.',
|
||||
],
|
||||
'teams.memberships.delete' => [
|
||||
'description' => 'This event triggers when a team memberships is deleted.',
|
||||
],
|
||||
];
|
|
@ -105,6 +105,10 @@ App::post('/v1/account')
|
|||
|
||||
Authorization::enable();
|
||||
|
||||
Authorization::unsetRole('role:'.Auth::USER_ROLE_GUEST);
|
||||
Authorization::setRole('user:'.$user->getId());
|
||||
Authorization::setRole('role:'.Auth::USER_ROLE_MEMBER);
|
||||
|
||||
if (false === $user) {
|
||||
throw new Exception('Failed saving user to DB', 500);
|
||||
}
|
||||
|
@ -115,10 +119,6 @@ App::post('/v1/account')
|
|||
->setParam('resource', 'users/'.$user->getId())
|
||||
;
|
||||
|
||||
$user
|
||||
->setAttribute('roles', Authorization::getRoles())
|
||||
;
|
||||
|
||||
$response
|
||||
->setStatusCode(Response::STATUS_CODE_CREATED)
|
||||
->dynamic($user, Response::MODEL_USER)
|
||||
|
@ -190,12 +190,12 @@ App::post('/v1/account/sessions')
|
|||
$session = new Document([
|
||||
'$collection' => Database::SYSTEM_COLLECTION_TOKENS,
|
||||
'$permissions' => ['read' => ['user:'.$profile->getId()], 'write' => ['user:'.$profile->getId()]],
|
||||
'userId' => $profile->getId(),
|
||||
'type' => Auth::TOKEN_TYPE_LOGIN,
|
||||
'secret' => Auth::hash($secret), // One way hash encryption to protect DB leak
|
||||
'expire' => $expiry,
|
||||
'userAgent' => $request->getUserAgent('UNKNOWN'),
|
||||
'ip' => $request->getIP(),
|
||||
|
||||
'osCode' => $osCode,
|
||||
'osName' => $osName,
|
||||
'osVersion' => $osVersion,
|
||||
|
@ -505,7 +505,6 @@ App::get('/v1/account/sessions/oauth2/:provider/redirect')
|
|||
|
||||
// Create session token, verify user account and update OAuth2 ID and Access Token
|
||||
|
||||
|
||||
$dd = new DeviceDetector($request->getUserAgent('UNKNOWN'));
|
||||
|
||||
$dd->parse();
|
||||
|
@ -528,12 +527,12 @@ App::get('/v1/account/sessions/oauth2/:provider/redirect')
|
|||
$session = new Document([
|
||||
'$collection' => Database::SYSTEM_COLLECTION_TOKENS,
|
||||
'$permissions' => ['read' => ['user:'.$user['$id']], 'write' => ['user:'.$user['$id']]],
|
||||
'userId' => $user->getId(),
|
||||
'type' => Auth::TOKEN_TYPE_LOGIN,
|
||||
'secret' => Auth::hash($secret), // One way hash encryption to protect DB leak
|
||||
'expire' => $expiry,
|
||||
'userAgent' => $request->getUserAgent('UNKNOWN'),
|
||||
'ip' => $request->getIP(),
|
||||
|
||||
'osCode' => $osCode,
|
||||
'osName' => $osName,
|
||||
'osVersion' => $osVersion,
|
||||
|
@ -624,10 +623,6 @@ App::get('/v1/account')
|
|||
/** @var Appwrite\Utopia\Response $response */
|
||||
/** @var Appwrite\Database\Document $user */
|
||||
|
||||
$user
|
||||
->setAttribute('roles', Authorization::getRoles())
|
||||
;
|
||||
|
||||
$response->dynamic($user, Response::MODEL_USER);
|
||||
}, ['response', 'user']);
|
||||
|
||||
|
@ -818,8 +813,6 @@ App::patch('/v1/account/name')
|
|||
throw new Exception('Failed saving user to DB', 500);
|
||||
}
|
||||
|
||||
$user->setAttribute('roles', Authorization::getRoles());
|
||||
|
||||
$audits
|
||||
->setParam('userId', $user->getId())
|
||||
->setParam('event', 'account.update.name')
|
||||
|
@ -861,8 +854,6 @@ App::patch('/v1/account/password')
|
|||
throw new Exception('Failed saving user to DB', 500);
|
||||
}
|
||||
|
||||
$user->setAttribute('roles', Authorization::getRoles());
|
||||
|
||||
$audits
|
||||
->setParam('userId', $user->getId())
|
||||
->setParam('event', 'account.update.password')
|
||||
|
@ -918,8 +909,6 @@ App::patch('/v1/account/email')
|
|||
if (false === $user) {
|
||||
throw new Exception('Failed saving user to DB', 500);
|
||||
}
|
||||
|
||||
$user->setAttribute('roles', Authorization::getRoles());
|
||||
|
||||
$audits
|
||||
->setParam('userId', $user->getId())
|
||||
|
@ -962,9 +951,7 @@ App::patch('/v1/account/prefs')
|
|||
->setParam('resource', 'users/'.$user->getId())
|
||||
;
|
||||
|
||||
$prefs = $user->getAttribute('prefs', new \stdClass);
|
||||
|
||||
$response->dynamic(new Document($prefs), Response::MODEL_ANY);
|
||||
$response->dynamic($user, Response::MODEL_USER);
|
||||
}, ['response', 'user', 'projectDB', 'audits']);
|
||||
|
||||
App::delete('/v1/account')
|
||||
|
@ -1069,23 +1056,27 @@ App::delete('/v1/account/sessions/:sessionId')
|
|||
->setParam('resource', '/user/'.$user->getId())
|
||||
;
|
||||
|
||||
$webhooks
|
||||
->setParam('payload', $response->output($user, Response::MODEL_USER))
|
||||
;
|
||||
|
||||
if (!Config::getParam('domainVerification')) {
|
||||
$response
|
||||
->addHeader('X-Fallback-Cookies', \json_encode([]))
|
||||
;
|
||||
}
|
||||
|
||||
$token->setAttribute('current', false);
|
||||
|
||||
if ($token->getAttribute('secret') == Auth::hash(Auth::$secret)) { // If current session delete the cookies too
|
||||
$token->setAttribute('current', true);
|
||||
|
||||
$response
|
||||
->addCookie(Auth::$cookieName.'_legacy', '', \time() - 3600, '/', Config::getParam('cookieDomain'), ('https' == $protocol), true, null)
|
||||
->addCookie(Auth::$cookieName, '', \time() - 3600, '/', Config::getParam('cookieDomain'), ('https' == $protocol), true, Config::getParam('cookieSamesite'))
|
||||
;
|
||||
}
|
||||
|
||||
$webhooks
|
||||
->setParam('payload', $response->output($token, Response::MODEL_SESSION))
|
||||
;
|
||||
|
||||
return $response->noContent();
|
||||
}
|
||||
}
|
||||
|
@ -1127,10 +1118,6 @@ App::delete('/v1/account/sessions')
|
|||
->setParam('event', 'account.sessions.delete')
|
||||
->setParam('resource', '/user/'.$user->getId())
|
||||
;
|
||||
|
||||
$webhooks
|
||||
->setParam('payload', $response->output($user, Response::MODEL_USER))
|
||||
;
|
||||
|
||||
if (!Config::getParam('domainVerification')) {
|
||||
$response
|
||||
|
@ -1138,13 +1125,23 @@ App::delete('/v1/account/sessions')
|
|||
;
|
||||
}
|
||||
|
||||
$token->setAttribute('current', false);
|
||||
|
||||
if ($token->getAttribute('secret') == Auth::hash(Auth::$secret)) { // If current session delete the cookies too
|
||||
$token->setAttribute('current', true);
|
||||
$response
|
||||
->addCookie(Auth::$cookieName.'_legacy', '', \time() - 3600, '/', Config::getParam('cookieDomain'), ('https' == $protocol), true, null)
|
||||
->addCookie(Auth::$cookieName, '', \time() - 3600, '/', Config::getParam('cookieDomain'), ('https' == $protocol), true, Config::getParam('cookieSamesite'))
|
||||
;
|
||||
}
|
||||
}
|
||||
|
||||
$webhooks
|
||||
->setParam('payload', $response->output(new Document([
|
||||
'sum' => count($tokens),
|
||||
'sessions' => $tokens
|
||||
]), Response::MODEL_SESSION_LIST))
|
||||
;
|
||||
|
||||
$response->noContent();
|
||||
}, ['request', 'response', 'user', 'projectDB', 'audits', 'webhooks']);
|
||||
|
@ -1153,6 +1150,7 @@ App::post('/v1/account/recovery')
|
|||
->desc('Create Password Recovery')
|
||||
->groups(['api', 'account'])
|
||||
->label('scope', 'public')
|
||||
->label('event', 'account.recovery.create')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT])
|
||||
->label('sdk.namespace', 'account')
|
||||
->label('sdk.method', 'createRecovery')
|
||||
|
@ -1164,7 +1162,7 @@ App::post('/v1/account/recovery')
|
|||
->label('abuse-key', 'url:{url},email:{param-email}')
|
||||
->param('email', '', new Email(), 'User email.')
|
||||
->param('url', '', function ($clients) { return new Host($clients); }, 'URL to redirect the user back to your app from the recovery email. Only URLs from hostnames in your project platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API.', false, ['clients'])
|
||||
->action(function ($email, $url, $request, $response, $projectDB, $project, $locale, $mails, $audits) {
|
||||
->action(function ($email, $url, $request, $response, $projectDB, $project, $locale, $mails, $audits, $webhooks) {
|
||||
/** @var Utopia\Swoole\Request $request */
|
||||
/** @var Appwrite\Utopia\Response $response */
|
||||
/** @var Appwrite\Database\Database $projectDB */
|
||||
|
@ -1172,6 +1170,10 @@ App::post('/v1/account/recovery')
|
|||
/** @var Utopia\Locale\Locale $locale */
|
||||
/** @var Appwrite\Event\Event $mails */
|
||||
/** @var Appwrite\Event\Event $audits */
|
||||
/** @var Appwrite\Event\Event $webhooks */
|
||||
|
||||
$isPreviliggedUser = Auth::isPreviliggedUser(Authorization::$roles);
|
||||
$isAppUser = Auth::isAppUser(Authorization::$roles);
|
||||
|
||||
$profile = $projectDB->getCollectionFirst([ // Get user by email address
|
||||
'limit' => 1,
|
||||
|
@ -1189,6 +1191,7 @@ App::post('/v1/account/recovery')
|
|||
$recovery = new Document([
|
||||
'$collection' => Database::SYSTEM_COLLECTION_TOKENS,
|
||||
'$permissions' => ['read' => ['user:'.$profile->getId()], 'write' => ['user:'.$profile->getId()]],
|
||||
'userId' => $profile->getId(),
|
||||
'type' => Auth::TOKEN_TYPE_RECOVERY,
|
||||
'secret' => Auth::hash($secret), // One way hash encryption to protect DB leak
|
||||
'expire' => \time() + Auth::TOKEN_EXPIRATION_RECOVERY,
|
||||
|
@ -1246,6 +1249,17 @@ App::post('/v1/account/recovery')
|
|||
->trigger();
|
||||
;
|
||||
|
||||
$webhooks
|
||||
->setParam('payload',
|
||||
$response->output($recovery->setAttribute('secret', $secret),
|
||||
Response::MODEL_TOKEN
|
||||
))
|
||||
;
|
||||
|
||||
$recovery // Hide secret for clients, sp
|
||||
->setAttribute('secret',
|
||||
($isPreviliggedUser || $isAppUser) ? $secret : '');
|
||||
|
||||
$audits
|
||||
->setParam('userId', $profile->getId())
|
||||
->setParam('event', 'account.recovery.create')
|
||||
|
@ -1256,12 +1270,13 @@ App::post('/v1/account/recovery')
|
|||
->setStatusCode(Response::STATUS_CODE_CREATED)
|
||||
->dynamic($recovery, Response::MODEL_TOKEN)
|
||||
;
|
||||
}, ['request', 'response', 'projectDB', 'project', 'locale', 'mails', 'audits']);
|
||||
}, ['request', 'response', 'projectDB', 'project', 'locale', 'mails', 'audits', 'webhooks']);
|
||||
|
||||
App::put('/v1/account/recovery')
|
||||
->desc('Complete Password Recovery')
|
||||
->groups(['api', 'account'])
|
||||
->label('scope', 'public')
|
||||
->label('event', 'account.recovery.update')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT])
|
||||
->label('sdk.namespace', 'account')
|
||||
->label('sdk.method', 'updateRecovery')
|
||||
|
@ -1337,6 +1352,7 @@ App::post('/v1/account/verification')
|
|||
->desc('Create Email Verification')
|
||||
->groups(['api', 'account'])
|
||||
->label('scope', 'account')
|
||||
->label('event', 'account.verification.create')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT])
|
||||
->label('sdk.namespace', 'account')
|
||||
->label('sdk.method', 'createVerification')
|
||||
|
@ -1347,7 +1363,7 @@ App::post('/v1/account/verification')
|
|||
->label('abuse-limit', 10)
|
||||
->label('abuse-key', 'url:{url},email:{param-email}')
|
||||
->param('url', '', function ($clients) { return new Host($clients); }, 'URL to redirect the user back to your app from the verification email. Only URLs from hostnames in your project platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API.', false, ['clients']) // TODO add built-in confirm page
|
||||
->action(function ($url, $request, $response, $project, $user, $projectDB, $locale, $audits, $mails) {
|
||||
->action(function ($url, $request, $response, $project, $user, $projectDB, $locale, $audits, $webhooks, $mails) {
|
||||
/** @var Utopia\Swoole\Request $request */
|
||||
/** @var Appwrite\Utopia\Response $response */
|
||||
/** @var Appwrite\Database\Document $project */
|
||||
|
@ -1355,13 +1371,18 @@ App::post('/v1/account/verification')
|
|||
/** @var Appwrite\Database\Database $projectDB */
|
||||
/** @var Utopia\Locale\Locale $locale */
|
||||
/** @var Appwrite\Event\Event $audits */
|
||||
/** @var Appwrite\Event\Event $webhooks */
|
||||
/** @var Appwrite\Event\Event $mails */
|
||||
|
||||
$isPreviliggedUser = Auth::isPreviliggedUser(Authorization::$roles);
|
||||
$isAppUser = Auth::isAppUser(Authorization::$roles);
|
||||
|
||||
$verificationSecret = Auth::tokenGenerator();
|
||||
|
||||
$verification = new Document([
|
||||
'$collection' => Database::SYSTEM_COLLECTION_TOKENS,
|
||||
'$permissions' => ['read' => ['user:'.$user->getId()], 'write' => ['user:'.$user->getId()]],
|
||||
'userId' => $user->getId(),
|
||||
'type' => Auth::TOKEN_TYPE_VERIFICATION,
|
||||
'secret' => Auth::hash($verificationSecret), // One way hash encryption to protect DB leak
|
||||
'expire' => \time() + Auth::TOKEN_EXPIRATION_CONFIRM,
|
||||
|
@ -1419,6 +1440,17 @@ App::post('/v1/account/verification')
|
|||
->trigger()
|
||||
;
|
||||
|
||||
$webhooks
|
||||
->setParam('payload',
|
||||
$response->output($verification->setAttribute('secret', $verificationSecret),
|
||||
Response::MODEL_TOKEN
|
||||
))
|
||||
;
|
||||
|
||||
$verification // Hide secret for clients, sp
|
||||
->setAttribute('secret',
|
||||
($isPreviliggedUser || $isAppUser) ? $verificationSecret : '');
|
||||
|
||||
$audits
|
||||
->setParam('userId', $user->getId())
|
||||
->setParam('event', 'account.verification.create')
|
||||
|
@ -1429,12 +1461,13 @@ App::post('/v1/account/verification')
|
|||
->setStatusCode(Response::STATUS_CODE_CREATED)
|
||||
->dynamic($verification, Response::MODEL_TOKEN)
|
||||
;
|
||||
}, ['request', 'response', 'project', 'user', 'projectDB', 'locale', 'audits', 'mails']);
|
||||
}, ['request', 'response', 'project', 'user', 'projectDB', 'locale', 'audits', 'webhooks', 'mails']);
|
||||
|
||||
App::put('/v1/account/verification')
|
||||
->desc('Complete Email Verification')
|
||||
->groups(['api', 'account'])
|
||||
->label('scope', 'public')
|
||||
->label('event', 'account.verification.update')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT])
|
||||
->label('sdk.namespace', 'account')
|
||||
->label('sdk.method', 'updateVerification')
|
||||
|
|
|
@ -23,6 +23,7 @@ use DeviceDetector\DeviceDetector;
|
|||
App::post('/v1/teams')
|
||||
->desc('Create Team')
|
||||
->groups(['api', 'teams'])
|
||||
->label('event', 'teams.create')
|
||||
->label('scope', 'teams.write')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT, APP_PLATFORM_SERVER])
|
||||
->label('sdk.namespace', 'teams')
|
||||
|
@ -157,6 +158,7 @@ App::get('/v1/teams/:teamId')
|
|||
App::put('/v1/teams/:teamId')
|
||||
->desc('Update Team')
|
||||
->groups(['api', 'teams'])
|
||||
->label('event', 'teams.update')
|
||||
->label('scope', 'teams.write')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT, APP_PLATFORM_SERVER])
|
||||
->label('sdk.namespace', 'teams')
|
||||
|
@ -191,6 +193,7 @@ App::put('/v1/teams/:teamId')
|
|||
App::delete('/v1/teams/:teamId')
|
||||
->desc('Delete Team')
|
||||
->groups(['api', 'teams'])
|
||||
->label('event', 'teams.delete')
|
||||
->label('scope', 'teams.write')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT, APP_PLATFORM_SERVER])
|
||||
->label('sdk.namespace', 'teams')
|
||||
|
@ -200,9 +203,10 @@ App::delete('/v1/teams/:teamId')
|
|||
->label('sdk.response.type', Response::CONTENT_TYPE_JSON)
|
||||
->label('sdk.response.model', Response::MODEL_NONE)
|
||||
->param('teamId', '', new UID(), 'Team unique ID.')
|
||||
->action(function ($teamId, $response, $projectDB) {
|
||||
->action(function ($teamId, $response, $projectDB, $webhooks) {
|
||||
/** @var Appwrite\Utopia\Response $response */
|
||||
/** @var Appwrite\Database\Database $projectDB */
|
||||
/** @var Appwrite\Event\Event $webhooks */
|
||||
|
||||
$team = $projectDB->getDocument($teamId);
|
||||
|
||||
|
@ -229,12 +233,17 @@ App::delete('/v1/teams/:teamId')
|
|||
throw new Exception('Failed to remove team from DB', 500);
|
||||
}
|
||||
|
||||
$webhooks
|
||||
->setParam('payload', $response->output($team, Response::MODEL_TEAM))
|
||||
;
|
||||
|
||||
$response->noContent();
|
||||
}, ['response', 'projectDB']);
|
||||
}, ['response', 'projectDB', 'webhooks']);
|
||||
|
||||
App::post('/v1/teams/:teamId/memberships')
|
||||
->desc('Create Team Membership')
|
||||
->groups(['api', 'teams'])
|
||||
->label('event', 'teams.memberships.create')
|
||||
->label('scope', 'teams.write')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT, APP_PLATFORM_SERVER])
|
||||
->label('sdk.namespace', 'teams')
|
||||
|
@ -482,6 +491,7 @@ App::get('/v1/teams/:teamId/memberships')
|
|||
App::patch('/v1/teams/:teamId/memberships/:inviteId/status')
|
||||
->desc('Update Team Membership Status')
|
||||
->groups(['api', 'teams'])
|
||||
->label('event', 'teams.memberships.update.status')
|
||||
->label('scope', 'public')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT])
|
||||
->label('sdk.namespace', 'teams')
|
||||
|
@ -580,6 +590,7 @@ App::patch('/v1/teams/:teamId/memberships/:inviteId/status')
|
|||
$session = new Document([
|
||||
'$collection' => Database::SYSTEM_COLLECTION_TOKENS,
|
||||
'$permissions' => ['read' => ['user:'.$user->getId()], 'write' => ['user:'.$user->getId()]],
|
||||
'userId' => $user->getId(),
|
||||
'type' => Auth::TOKEN_TYPE_LOGIN,
|
||||
'secret' => Auth::hash($secret), // One way hash encryption to protect DB leak
|
||||
'expire' => $expiry,
|
||||
|
@ -660,6 +671,7 @@ App::patch('/v1/teams/:teamId/memberships/:inviteId/status')
|
|||
App::delete('/v1/teams/:teamId/memberships/:inviteId')
|
||||
->desc('Delete Team Membership')
|
||||
->groups(['api', 'teams'])
|
||||
->label('event', 'teams.memberships.delete')
|
||||
->label('scope', 'teams.write')
|
||||
->label('sdk.platform', [APP_PLATFORM_CLIENT, APP_PLATFORM_SERVER])
|
||||
->label('sdk.namespace', 'teams')
|
||||
|
@ -670,10 +682,11 @@ App::delete('/v1/teams/:teamId/memberships/:inviteId')
|
|||
->label('sdk.response.model', Response::MODEL_NONE)
|
||||
->param('teamId', '', new UID(), 'Team unique ID.')
|
||||
->param('inviteId', '', new UID(), 'Invite unique ID.')
|
||||
->action(function ($teamId, $inviteId, $response, $projectDB, $audits) {
|
||||
->action(function ($teamId, $inviteId, $response, $projectDB, $audits, $webhooks) {
|
||||
/** @var Appwrite\Utopia\Response $response */
|
||||
/** @var Appwrite\Database\Database $projectDB */
|
||||
/** @var Appwrite\Event\Event $audits */
|
||||
/** @var Appwrite\Event\Event $webhooks */
|
||||
|
||||
$membership = $projectDB->getDocument($inviteId);
|
||||
|
||||
|
@ -711,5 +724,9 @@ App::delete('/v1/teams/:teamId/memberships/:inviteId')
|
|||
->setParam('resource', 'teams/'.$teamId)
|
||||
;
|
||||
|
||||
$webhooks
|
||||
->setParam('payload', $response->output($membership, Response::MODEL_MEMBERSHIP))
|
||||
;
|
||||
|
||||
$response->noContent();
|
||||
}, ['response', 'projectDB', 'audits']);
|
||||
}, ['response', 'projectDB', 'audits', 'webhooks']);
|
||||
|
|
|
@ -172,7 +172,7 @@ App::init(function ($utopia, $request, $response, $console, $project, $user, $lo
|
|||
*/
|
||||
if (null !== $key && $user->isEmpty()) {
|
||||
$user = new Document([
|
||||
'$id' => 0,
|
||||
'$id' => '',
|
||||
'status' => Auth::USER_STATUS_ACTIVATED,
|
||||
'email' => 'app.'.$project->getId().'@service.'.$request->getHostname(),
|
||||
'password' => '',
|
||||
|
@ -233,6 +233,7 @@ App::init(function ($utopia, $request, $response, $console, $project, $user, $lo
|
|||
|
||||
$webhooks
|
||||
->setParam('projectId', $project->getId())
|
||||
->setParam('userId', $user->getId())
|
||||
->setParam('event', $route->getLabel('event', ''))
|
||||
->setParam('payload', [])
|
||||
;
|
||||
|
@ -301,8 +302,8 @@ App::shutdown(function ($utopia, $request, $response, $project, $webhooks, $audi
|
|||
$route = $utopia->match($request);
|
||||
|
||||
if ($project->getId()
|
||||
&& $mode !== APP_MODE_ADMIN
|
||||
&& !empty($route->getLabel('sdk.namespace', null))) { // Don't calculate console usage and admin mode
|
||||
&& $mode !== APP_MODE_ADMIN //TODO: add check to make sure user is admin
|
||||
&& !empty($route->getLabel('sdk.namespace', null))) { // Don't calculate console usage on admin mode
|
||||
|
||||
$usage
|
||||
->setParam('networkRequestSize', $request->getSize() + $usage->getParam('storage'))
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
<?php
|
||||
|
||||
use Utopia\App;
|
||||
use Utopia\CLI\Console;
|
||||
|
||||
require_once __DIR__.'/../init.php';
|
||||
|
||||
|
@ -23,6 +24,11 @@ class MailsV1
|
|||
{
|
||||
global $register;
|
||||
|
||||
if(empty(App::getEnv('_APP_SMTP_HOST'))) {
|
||||
Console::info('Skipped mail processing. No SMTP server hostname has been set.');
|
||||
return;
|
||||
}
|
||||
|
||||
$event = $this->args['event'];
|
||||
$from = $this->args['from'];
|
||||
$recipient = $this->args['recipient'];
|
||||
|
|
|
@ -34,8 +34,9 @@ class WebhooksV1
|
|||
$errors = [];
|
||||
|
||||
// Event
|
||||
$projectId = $this->args['projectId'];
|
||||
$event = $this->args['event'];
|
||||
$projectId = $this->args['projectId'] ?? '';
|
||||
$userId = $this->args['userId'] ?? '';
|
||||
$event = $this->args['event'] ?? '';
|
||||
$payload = \json_encode($this->args['payload']);
|
||||
|
||||
// Webhook
|
||||
|
@ -55,6 +56,7 @@ class WebhooksV1
|
|||
continue;
|
||||
}
|
||||
|
||||
$id = $webhook['$id'] ?? '';
|
||||
$name = $webhook['name'] ?? '';
|
||||
$signature = $webhook['signature'] ?? 'not-yet-implemented';
|
||||
$url = $webhook['url'] ?? '';
|
||||
|
@ -78,8 +80,11 @@ class WebhooksV1
|
|||
[
|
||||
'Content-Type: application/json',
|
||||
'Content-Length: '.\strlen($payload),
|
||||
'X-'.APP_NAME.'-Webhook-Id: '.$id,
|
||||
'X-'.APP_NAME.'-Webhook-Event: '.$event,
|
||||
'X-'.APP_NAME.'-Webhook-Name: '.$name,
|
||||
'X-'.APP_NAME.'-Webhook-User-Id: '.$userId,
|
||||
'X-'.APP_NAME.'-Webhook-Project-Id: '.$projectId,
|
||||
'X-'.APP_NAME.'-Webhook-Signature: '.$signature,
|
||||
]
|
||||
);
|
||||
|
|
|
@ -112,7 +112,7 @@ If running in production, it might be easier to use a 3rd party SMTP server as i
|
|||
|
||||
### _APP_SMTP_HOST
|
||||
|
||||
SMTP server host name address. Default value is: 'smtp'
|
||||
SMTP server host name address. Default value is: 'smtp'. Pass an empty string to disable all mail sending from the server.
|
||||
|
||||
### _APP_SMTP_PORT
|
||||
|
||||
|
|
|
@ -97,6 +97,16 @@ class Authorization extends Validator
|
|||
self::$roles[$role] = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param string $role
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public static function unsetRole(string $role): void
|
||||
{
|
||||
unset(self::$roles[$role]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return array
|
||||
*/
|
||||
|
|
|
@ -261,7 +261,8 @@ class Response extends SwooleResponse
|
|||
$output = [];
|
||||
|
||||
if ($model->isAny()) {
|
||||
return $document->getArrayCopy();
|
||||
$this->payload = $document->getArrayCopy();
|
||||
return $this->payload;
|
||||
}
|
||||
|
||||
foreach ($model->getRules() as $key => $rule) {
|
||||
|
@ -294,7 +295,7 @@ class Response extends SwooleResponse
|
|||
|
||||
$this->payload = $output;
|
||||
|
||||
return $output;
|
||||
return $this->payload;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -15,6 +15,12 @@ class Session extends Model
|
|||
'description' => 'Session ID.',
|
||||
'example' => '5e5ea5c16897e',
|
||||
])
|
||||
->addRule('userId', [
|
||||
'type' => self::TYPE_STRING,
|
||||
'description' => 'User ID.',
|
||||
'default' => '',
|
||||
'example' => '5e5bb8c16897e',
|
||||
])
|
||||
->addRule('expire', [
|
||||
'type' => self::TYPE_INTEGER,
|
||||
'description' => 'Session expiration date in Unix timestamp.',
|
||||
|
@ -114,7 +120,7 @@ class Session extends Model
|
|||
->addRule('current', [
|
||||
'type' => self::TYPE_BOOLEAN,
|
||||
'description' => 'Returns true if this the current user session.',
|
||||
'default' => '',
|
||||
'default' => false,
|
||||
'example' => true,
|
||||
])
|
||||
;
|
||||
|
|
|
@ -13,14 +13,19 @@ class Token extends Model
|
|||
->addRule('$id', [
|
||||
'type' => self::TYPE_STRING,
|
||||
'description' => 'Token ID.',
|
||||
'example' => '5e5ea5c16897e',
|
||||
'example' => 'bb8ea5c16897e',
|
||||
])
|
||||
->addRule('userId', [
|
||||
'type' => self::TYPE_STRING,
|
||||
'description' => 'User ID.',
|
||||
'example' => '5e5ea5c168bb8',
|
||||
])
|
||||
->addRule('secret', [
|
||||
'type' => self::TYPE_STRING,
|
||||
'description' => 'Token secret key. This will return an empty string unless the response is returned using an API key or as part of a webhook payload.',
|
||||
'default' => 0,
|
||||
'example' => '',
|
||||
])
|
||||
// ->addRule('type', [ TODO: use this when token types will be strings
|
||||
// 'type' => self::TYPE_STRING,
|
||||
// 'description' => 'Token type. Possible values: play, pause',
|
||||
// 'default' => '',
|
||||
// 'example' => '127.0.0.1',
|
||||
// ])
|
||||
->addRule('expire', [
|
||||
'type' => self::TYPE_INTEGER,
|
||||
'description' => 'Token expiration date in Unix timestamp.',
|
||||
|
|
|
@ -47,13 +47,6 @@ class User extends Model
|
|||
'default' => new \stdClass,
|
||||
'example' => ['theme' => 'pink', 'timezone' => 'UTC'],
|
||||
])
|
||||
->addRule('roles', [
|
||||
'type' => self::TYPE_STRING,
|
||||
'description' => 'User list of roles',
|
||||
'default' => [],
|
||||
'example' => '*',
|
||||
'array' => true,
|
||||
])
|
||||
;
|
||||
}
|
||||
|
||||
|
|
|
@ -81,23 +81,64 @@ trait ProjectCustom
|
|||
],
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $project['headers']['status-code']);
|
||||
$this->assertEquals(201, $key['headers']['status-code']);
|
||||
$this->assertNotEmpty($key['body']);
|
||||
$this->assertNotEmpty($key['body']['secret']);
|
||||
|
||||
// return [
|
||||
// 'email' => $this->demoEmail,
|
||||
// 'password' => $this->demoPassword,
|
||||
// 'session' => $session,
|
||||
// 'projectUid' => $project['body']['$id'],
|
||||
// 'projectAPIKeySecret' => $key['body']['secret'],
|
||||
// 'projectSession' => $this->client->parseCookie($user['headers']['set-cookie'])['a_session_' . $project['body']['$id']],
|
||||
// ];
|
||||
$webhook = $this->client->call(Client::METHOD_POST, '/projects/'.$project['body']['$id'].'/webhooks', [
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'cookie' => 'a_session_console=' . $this->getRoot()['session'],
|
||||
'x-appwrite-project' => 'console',
|
||||
], [
|
||||
'name' => 'Webhook Test',
|
||||
'events' => [
|
||||
'account.create',
|
||||
'account.update.email',
|
||||
'account.update.name',
|
||||
'account.update.password',
|
||||
'account.update.prefs',
|
||||
'account.recovery.create',
|
||||
'account.recovery.update',
|
||||
'account.verification.create',
|
||||
'account.verification.update',
|
||||
'account.delete',
|
||||
'account.sessions.create',
|
||||
'account.sessions.delete',
|
||||
'database.collections.create',
|
||||
'database.collections.update',
|
||||
'database.collections.delete',
|
||||
'database.documents.create',
|
||||
'database.documents.update',
|
||||
'database.documents.delete',
|
||||
'storage.files.create',
|
||||
'storage.files.update',
|
||||
'storage.files.delete',
|
||||
'users.create',
|
||||
'users.update.status',
|
||||
'users.delete',
|
||||
'users.sessions.delete',
|
||||
'teams.create',
|
||||
'teams.update',
|
||||
'teams.delete',
|
||||
'teams.memberships.create',
|
||||
'teams.memberships.update.status',
|
||||
'teams.memberships.delete',
|
||||
],
|
||||
'url' => 'http://request-catcher:5000/webhook',
|
||||
'security' => false,
|
||||
'httpUser' => '',
|
||||
'httpPass' => '',
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $webhook['headers']['status-code']);
|
||||
$this->assertNotEmpty($webhook['body']);
|
||||
|
||||
self::$project = [
|
||||
'$id' => $project['body']['$id'],
|
||||
'name' => $project['body']['name'],
|
||||
'apiKey' => $key['body']['secret'],
|
||||
'webhookId' => $webhook['body']['$id'],
|
||||
];
|
||||
|
||||
return self::$project;
|
||||
|
|
|
@ -46,7 +46,7 @@ abstract class Scope extends TestCase
|
|||
|
||||
protected function getLastRequest():array
|
||||
{
|
||||
sleep(10);
|
||||
sleep(5);
|
||||
|
||||
$resquest = json_decode(file_get_contents('http://request-catcher:5000/__last_request__'), true);
|
||||
$resquest['data'] = json_decode($resquest['data'], true);
|
||||
|
|
|
@ -11,4 +11,12 @@ trait SideClient
|
|||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $this->getUser()['session'],
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @return string
|
||||
*/
|
||||
public function getSide()
|
||||
{
|
||||
return 'client';
|
||||
}
|
||||
}
|
||||
|
|
|
@ -8,4 +8,12 @@ trait SideNone
|
|||
{
|
||||
return [];
|
||||
}
|
||||
|
||||
/**
|
||||
* @return string
|
||||
*/
|
||||
public function getSide()
|
||||
{
|
||||
return 'none';
|
||||
}
|
||||
}
|
||||
|
|
|
@ -15,4 +15,12 @@ trait SideServer
|
|||
'x-appwrite-key' => $this->getProject()['apiKey']
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @return string
|
||||
*/
|
||||
public function getSide()
|
||||
{
|
||||
return 'server';
|
||||
}
|
||||
}
|
||||
|
|
|
@ -152,10 +152,6 @@ trait AccountBase
|
|||
$this->assertIsNumeric($response['body']['registration']);
|
||||
$this->assertEquals($response['body']['email'], $email);
|
||||
$this->assertEquals($response['body']['name'], $name);
|
||||
$this->assertContains('*', $response['body']['roles']);
|
||||
$this->assertContains('user:'.$response['body']['$id'], $response['body']['roles']);
|
||||
$this->assertContains('role:1', $response['body']['roles']);
|
||||
$this->assertCount(3, $response['body']['roles']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
|
@ -573,8 +569,8 @@ trait AccountBase
|
|||
$this->assertIsArray($response['body']);
|
||||
$this->assertNotEmpty($response['body']);
|
||||
$this->assertNotEmpty($response['body']);
|
||||
$this->assertEquals('prefValue1', $response['body']['prefKey1']);
|
||||
$this->assertEquals('prefValue2', $response['body']['prefKey2']);
|
||||
$this->assertEquals('prefValue1', $response['body']['prefs']['prefKey1']);
|
||||
$this->assertEquals('prefValue2', $response['body']['prefs']['prefKey2']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
|
@ -648,6 +644,7 @@ trait AccountBase
|
|||
|
||||
$this->assertEquals(201, $response['headers']['status-code']);
|
||||
$this->assertNotEmpty($response['body']['$id']);
|
||||
$this->assertEmpty($response['body']['secret']);
|
||||
$this->assertIsNumeric($response['body']['expire']);
|
||||
|
||||
$lastEmail = $this->getLastEmail();
|
||||
|
@ -661,24 +658,24 @@ trait AccountBase
|
|||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
$response = $this->client->call(Client::METHOD_POST, '/account/recovery', array_merge([
|
||||
$response = $this->client->call(Client::METHOD_POST, '/account/verification', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'url' => 'localhost/recovery',
|
||||
'url' => 'localhost/verification',
|
||||
]);
|
||||
|
||||
$this->assertEquals(400, $response['headers']['status-code']);
|
||||
|
||||
$response = $this->client->call(Client::METHOD_POST, '/account/recovery', array_merge([
|
||||
$response = $this->client->call(Client::METHOD_POST, '/account/verification', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'url' => 'http://remotehost/recovery',
|
||||
'url' => 'http://remotehost/verification',
|
||||
]);
|
||||
|
||||
$this->assertEquals(400, $response['headers']['status-code']);
|
||||
|
@ -939,6 +936,7 @@ trait AccountBase
|
|||
|
||||
$this->assertEquals(201, $response['headers']['status-code']);
|
||||
$this->assertNotEmpty($response['body']['$id']);
|
||||
$this->assertEmpty($response['body']['secret']);
|
||||
$this->assertIsNumeric($response['body']['expire']);
|
||||
|
||||
$lastEmail = $this->getLastEmail();
|
||||
|
|
|
@ -25,7 +25,6 @@ trait UsersBase
|
|||
$this->assertEquals($user['body']['email'], 'users.service@example.com');
|
||||
$this->assertEquals($user['body']['status'], 0);
|
||||
$this->assertGreaterThan(0, $user['body']['registration']);
|
||||
$this->assertIsArray($user['body']['roles']);
|
||||
|
||||
return ['userId' => $user['body']['$id']];
|
||||
}
|
||||
|
@ -48,7 +47,6 @@ trait UsersBase
|
|||
$this->assertEquals($user['body']['email'], 'users.service@example.com');
|
||||
$this->assertEquals($user['body']['status'], 0);
|
||||
$this->assertGreaterThan(0, $user['body']['registration']);
|
||||
$this->assertIsArray($user['body']['roles']);
|
||||
|
||||
$sessions = $this->client->call(Client::METHOD_GET, '/users/' . $data['userId'] . '/sessions', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
|
|
552
tests/e2e/Services/Webhooks/WebhooksBase.php
Normal file
552
tests/e2e/Services/Webhooks/WebhooksBase.php
Normal file
|
@ -0,0 +1,552 @@
|
|||
<?php
|
||||
|
||||
namespace Tests\E2E\Services\Webhooks;
|
||||
|
||||
use CURLFile;
|
||||
use Tests\E2E\Client;
|
||||
|
||||
trait WebhooksBase
|
||||
{
|
||||
public function testCreateCollection(): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$actors = $this->client->call(Client::METHOD_POST, '/database/collections', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'x-appwrite-key' => $this->getProject()['apiKey']
|
||||
]), [
|
||||
'name' => 'Actors',
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
'rules' => [
|
||||
[
|
||||
'label' => 'First Name',
|
||||
'key' => 'firstName',
|
||||
'type' => 'text',
|
||||
'default' => '',
|
||||
'required' => true,
|
||||
'array' => false
|
||||
],
|
||||
[
|
||||
'label' => 'Last Name',
|
||||
'key' => 'lastName',
|
||||
'type' => 'text',
|
||||
'default' => '',
|
||||
'required' => true,
|
||||
'array' => false
|
||||
],
|
||||
],
|
||||
]);
|
||||
|
||||
$this->assertEquals($actors['headers']['status-code'], 201);
|
||||
$this->assertNotEmpty($actors['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'database.collections.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], 'Actors');
|
||||
$this->assertIsArray($webhook['data']['$permissions']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['read']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['read']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(2, $webhook['data']['rules']);
|
||||
|
||||
return array_merge(['actorsId' => $actors['body']['$id']]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateCollection
|
||||
*/
|
||||
public function testCreateDocument(array $data): array
|
||||
{
|
||||
$document = $this->client->call(Client::METHOD_POST, '/database/collections/' . $data['actorsId'] . '/documents', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'data' => [
|
||||
'firstName' => 'Chris',
|
||||
'lastName' => 'Evans',
|
||||
|
||||
],
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
]);
|
||||
|
||||
$this->assertEquals($document['headers']['status-code'], 201);
|
||||
$this->assertNotEmpty($document['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'database.documents.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['firstName'], 'Chris');
|
||||
$this->assertEquals($webhook['data']['lastName'], 'Evans');
|
||||
$this->assertIsArray($webhook['data']['$permissions']['read']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['read']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['write']);
|
||||
|
||||
$data['documentId'] = $document['body']['$id'];
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateDocument
|
||||
*/
|
||||
public function testUpdateDocument(array $data): array
|
||||
{
|
||||
$document = $this->client->call(Client::METHOD_PATCH, '/database/collections/' . $data['actorsId'] . '/documents/'.$data['documentId'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'data' => [
|
||||
'firstName' => 'Chris1',
|
||||
'lastName' => 'Evans2',
|
||||
],
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
]);
|
||||
|
||||
$this->assertEquals($document['headers']['status-code'], 200);
|
||||
$this->assertNotEmpty($document['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'database.documents.update');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['firstName'], 'Chris1');
|
||||
$this->assertEquals($webhook['data']['lastName'], 'Evans2');
|
||||
$this->assertIsArray($webhook['data']['$permissions']['read']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['read']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['write']);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateCollection
|
||||
*/
|
||||
public function testDeleteDocument(array $data): array
|
||||
{
|
||||
$document = $this->client->call(Client::METHOD_POST, '/database/collections/' . $data['actorsId'] . '/documents', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'data' => [
|
||||
'firstName' => 'Bradly',
|
||||
'lastName' => 'Cooper',
|
||||
|
||||
],
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
]);
|
||||
|
||||
$this->assertEquals($document['headers']['status-code'], 201);
|
||||
$this->assertNotEmpty($document['body']['$id']);
|
||||
|
||||
$document = $this->client->call(Client::METHOD_DELETE, '/database/collections/' . $data['actorsId'] . '/documents/' . $document['body']['$id'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()));
|
||||
|
||||
$this->assertEquals($document['headers']['status-code'], 204);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'database.documents.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['firstName'], 'Bradly');
|
||||
$this->assertEquals($webhook['data']['lastName'], 'Cooper');
|
||||
$this->assertIsArray($webhook['data']['$permissions']['read']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['read']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['write']);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
public function testCreateFile(): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$file = $this->client->call(Client::METHOD_POST, '/storage/files', array_merge([
|
||||
'content-type' => 'multipart/form-data',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'file' => new CURLFile(realpath(__DIR__ . '/../../../resources/logo.png'), 'image/png', 'logo.png'),
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
'folderId' => 'xyz',
|
||||
]);
|
||||
|
||||
$this->assertEquals($file['headers']['status-code'], 201);
|
||||
$this->assertNotEmpty($file['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'storage.files.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']);
|
||||
$this->assertEquals($webhook['data']['name'], 'logo.png');
|
||||
$this->assertIsInt($webhook['data']['dateCreated'], 'logo.png');
|
||||
$this->assertNotEmpty($webhook['data']['signature']);
|
||||
$this->assertEquals($webhook['data']['mimeType'], 'image/png');
|
||||
$this->assertEquals($webhook['data']['sizeOriginal'], 47218);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return ['fileId' => $file['body']['$id']];
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateFile
|
||||
*/
|
||||
public function testUpdateFile(array $data): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$file = $this->client->call(Client::METHOD_PUT, '/storage/files/' . $data['fileId'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
]);
|
||||
|
||||
$this->assertEquals($file['headers']['status-code'], 200);
|
||||
$this->assertNotEmpty($file['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'storage.files.update');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']);
|
||||
$this->assertEquals($webhook['data']['name'], 'logo.png');
|
||||
$this->assertIsInt($webhook['data']['dateCreated'], 'logo.png');
|
||||
$this->assertNotEmpty($webhook['data']['signature']);
|
||||
$this->assertEquals($webhook['data']['mimeType'], 'image/png');
|
||||
$this->assertEquals($webhook['data']['sizeOriginal'], 47218);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testUpdateFile
|
||||
*/
|
||||
public function testDeleteFile(array $data): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$file = $this->client->call(Client::METHOD_DELETE, '/storage/files/' . $data['fileId'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()));
|
||||
|
||||
$this->assertEquals(204, $file['headers']['status-code']);
|
||||
$this->assertEmpty($file['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'storage.files.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']);
|
||||
$this->assertEquals($webhook['data']['name'], 'logo.png');
|
||||
$this->assertIsInt($webhook['data']['dateCreated'], 'logo.png');
|
||||
$this->assertNotEmpty($webhook['data']['signature']);
|
||||
$this->assertEquals($webhook['data']['mimeType'], 'image/png');
|
||||
$this->assertEquals($webhook['data']['sizeOriginal'], 47218);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
public function testCreateTeam(): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$team = $this->client->call(Client::METHOD_POST, '/teams', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'name' => 'Arsenal'
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $team['headers']['status-code']);
|
||||
$this->assertNotEmpty($team['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'teams.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals('Arsenal', $webhook['data']['name']);
|
||||
$this->assertGreaterThan(-1, $webhook['data']['sum']);
|
||||
$this->assertIsInt($webhook['data']['sum']);
|
||||
$this->assertIsInt($webhook['data']['dateCreated']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return ['teamId' => $team['body']['$id']];
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateTeam
|
||||
*/
|
||||
public function testUpdateTeam($data): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$team = $this->client->call(Client::METHOD_PUT, '/teams/'.$data['teamId'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'name' => 'Demo New'
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $team['headers']['status-code']);
|
||||
$this->assertNotEmpty($team['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'teams.update');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals('Demo New', $webhook['data']['name']);
|
||||
$this->assertGreaterThan(-1, $webhook['data']['sum']);
|
||||
$this->assertIsInt($webhook['data']['sum']);
|
||||
$this->assertIsInt($webhook['data']['dateCreated']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return ['teamId' => $team['body']['$id']];
|
||||
}
|
||||
|
||||
public function testDeleteTeam(): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$team = $this->client->call(Client::METHOD_POST, '/teams', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'name' => 'Chelsea'
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $team['headers']['status-code']);
|
||||
$this->assertNotEmpty($team['body']['$id']);
|
||||
|
||||
$team = $this->client->call(Client::METHOD_DELETE, '/teams/'.$team['body']['$id'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()));
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'teams.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals('Chelsea', $webhook['data']['name']);
|
||||
$this->assertGreaterThan(-1, $webhook['data']['sum']);
|
||||
$this->assertIsInt($webhook['data']['sum']);
|
||||
$this->assertIsInt($webhook['data']['dateCreated']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return [];
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateTeam
|
||||
*/
|
||||
public function testCreateTeamMembership($data): array
|
||||
{
|
||||
$teamUid = $data['teamId'] ?? '';
|
||||
$email = uniqid().'friend@localhost.test';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$team = $this->client->call(Client::METHOD_POST, '/teams/'.$teamUid.'/memberships', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'email' => $email,
|
||||
'name' => 'Friend User',
|
||||
'roles' => ['admin', 'editor'],
|
||||
'url' => 'http://localhost:5000/join-us#title'
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $team['headers']['status-code']);
|
||||
$this->assertNotEmpty($team['body']['$id']);
|
||||
|
||||
$lastEmail = $this->getLastEmail();
|
||||
|
||||
$secret = substr($lastEmail['text'], strpos($lastEmail['text'], '&secret=', 0) + 8, 256);
|
||||
$inviteUid = substr($lastEmail['text'], strpos($lastEmail['text'], '?inviteId=', 0) + 10, 13);
|
||||
$userUid = substr($lastEmail['text'], strpos($lastEmail['text'], '&userId=', 0) + 8, 13);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'teams.memberships.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertNotEmpty($webhook['data']['teamId']);
|
||||
$this->assertCount(2, $webhook['data']['roles']);
|
||||
$this->assertIsInt($webhook['data']['joined']);
|
||||
$this->assertEquals(('server' === $this->getSide()), $webhook['data']['confirm']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return [
|
||||
'teamId' => $teamUid,
|
||||
'secret' => $secret,
|
||||
'inviteId' => $inviteUid,
|
||||
'userId' => $webhook['data']['userId'],
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateTeam
|
||||
*/
|
||||
public function testDeleteTeamMembership($data): array
|
||||
{
|
||||
$teamUid = $data['teamId'] ?? '';
|
||||
$email = uniqid().'friend@localhost.test';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$team = $this->client->call(Client::METHOD_POST, '/teams/'.$teamUid.'/memberships', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'email' => $email,
|
||||
'name' => 'Friend User',
|
||||
'roles' => ['admin', 'editor'],
|
||||
'url' => 'http://localhost:5000/join-us#title'
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $team['headers']['status-code']);
|
||||
$this->assertNotEmpty($team['body']['$id']);
|
||||
|
||||
$team = $this->client->call(Client::METHOD_DELETE, '/teams/'.$teamUid.'/memberships/'.$team['body']['$id'], array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()));
|
||||
|
||||
$this->assertEquals(204, $team['headers']['status-code']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'teams.memberships.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertNotEmpty($webhook['data']['teamId']);
|
||||
$this->assertCount(2, $webhook['data']['roles']);
|
||||
$this->assertIsInt($webhook['data']['joined']);
|
||||
$this->assertEquals(('server' === $this->getSide()), $webhook['data']['confirm']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return [];
|
||||
}
|
||||
}
|
757
tests/e2e/Services/Webhooks/WebhooksCustomClientTest.php
Normal file
757
tests/e2e/Services/Webhooks/WebhooksCustomClientTest.php
Normal file
|
@ -0,0 +1,757 @@
|
|||
<?php
|
||||
|
||||
namespace Tests\E2E\Services\Webhooks;
|
||||
|
||||
use Tests\E2E\Client;
|
||||
use Tests\E2E\Scopes\Scope;
|
||||
use Tests\E2E\Scopes\ProjectCustom;
|
||||
use Tests\E2E\Scopes\SideClient;
|
||||
|
||||
class WebhooksCustomClientTest extends Scope
|
||||
{
|
||||
use WebhooksBase;
|
||||
use ProjectCustom;
|
||||
use SideClient;
|
||||
|
||||
public function testCreateAccount():array
|
||||
{
|
||||
$email = uniqid().'user@localhost.test';
|
||||
$password = 'password';
|
||||
$name = 'User Name';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$account = $this->client->call(Client::METHOD_POST, '/account', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
'name' => $name,
|
||||
]);
|
||||
|
||||
$id = $account['body']['$id'];
|
||||
|
||||
$this->assertEquals($account['headers']['status-code'], 201);
|
||||
$this->assertNotEmpty($account['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id']), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], $name);
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 0);
|
||||
$this->assertEquals($webhook['data']['email'], $email);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
return [
|
||||
'id' => $id,
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
'name' => $name,
|
||||
];
|
||||
}
|
||||
|
||||
public function testDeleteAccount():array
|
||||
{
|
||||
$email = uniqid().'user1@localhost.test';
|
||||
$password = 'password';
|
||||
$name = 'User Name 1';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$account = $this->client->call(Client::METHOD_POST, '/account', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
'name' => $name,
|
||||
]);
|
||||
|
||||
$accountSession = $this->client->call(Client::METHOD_POST, '/account/sessions', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
]);
|
||||
|
||||
$this->assertEquals($accountSession['headers']['status-code'], 201);
|
||||
|
||||
$sessionId = $accountSession['body']['$id'];
|
||||
$session = $this->client->parseCookie((string)$accountSession['headers']['set-cookie'])['a_session_'.$this->getProject()['$id']];
|
||||
|
||||
$account = $this->client->call(Client::METHOD_DELETE, '/account', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]));
|
||||
|
||||
$this->assertEquals($account['headers']['status-code'], 204);
|
||||
$this->assertEmpty($account['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], $name);
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 2);
|
||||
$this->assertEquals($webhook['data']['email'], $email);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
return [];
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateAccount
|
||||
*/
|
||||
public function testCreateAccountSession($data):array
|
||||
{
|
||||
$email = $data['email'] ?? '';
|
||||
$password = $data['password'] ?? '';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$accountSession = $this->client->call(Client::METHOD_POST, '/account/sessions', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
]);
|
||||
|
||||
$this->assertEquals($accountSession['headers']['status-code'], 201);
|
||||
|
||||
$sessionId = $accountSession['body']['$id'];
|
||||
$session = $this->client->parseCookie((string)$accountSession['headers']['set-cookie'])['a_session_'.$this->getProject()['$id']];
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.sessions.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id']), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertIsInt($webhook['data']['expire']);
|
||||
$this->assertEquals($webhook['data']['ip'], '127.0.0.1');
|
||||
$this->assertNotEmpty($webhook['data']['osCode']);
|
||||
$this->assertIsString($webhook['data']['osCode']);
|
||||
$this->assertNotEmpty($webhook['data']['osName']);
|
||||
$this->assertIsString($webhook['data']['osName']);
|
||||
$this->assertNotEmpty($webhook['data']['osVersion']);
|
||||
$this->assertIsString($webhook['data']['osVersion']);
|
||||
$this->assertEquals($webhook['data']['clientType'], 'browser');
|
||||
$this->assertEquals($webhook['data']['clientCode'], 'CH');
|
||||
$this->assertEquals($webhook['data']['clientName'], 'Chrome');
|
||||
$this->assertNotEmpty($webhook['data']['clientVersion']);
|
||||
$this->assertIsString($webhook['data']['clientVersion']);
|
||||
$this->assertNotEmpty($webhook['data']['clientEngine']);
|
||||
$this->assertIsString($webhook['data']['clientEngine']);
|
||||
$this->assertIsString($webhook['data']['clientEngineVersion']);
|
||||
$this->assertIsString($webhook['data']['deviceName']);
|
||||
$this->assertIsString($webhook['data']['deviceBrand']);
|
||||
$this->assertIsString($webhook['data']['deviceModel']);
|
||||
$this->assertIsString($webhook['data']['countryCode']);
|
||||
$this->assertIsString($webhook['data']['countryName']);
|
||||
$this->assertEquals($webhook['data']['current'], true);
|
||||
|
||||
return array_merge($data, [
|
||||
'sessionId' => $sessionId,
|
||||
'session' => $session,
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateAccount
|
||||
*/
|
||||
public function testDeleteAccountSession($data):array
|
||||
{
|
||||
$email = $data['email'] ?? '';
|
||||
$password = $data['password'] ?? '';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$accountSession = $this->client->call(Client::METHOD_POST, '/account/sessions', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
]);
|
||||
|
||||
$sessionId = $accountSession['body']['$id'];
|
||||
$session = $this->client->parseCookie((string)$accountSession['headers']['set-cookie'])['a_session_'.$this->getProject()['$id']];
|
||||
|
||||
$this->assertEquals($accountSession['headers']['status-code'], 201);
|
||||
|
||||
$accountSession = $this->client->call(Client::METHOD_DELETE, '/account/sessions/'.$sessionId, array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]));
|
||||
|
||||
$this->assertEquals($accountSession['headers']['status-code'], 204);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.sessions.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertIsInt($webhook['data']['expire']);
|
||||
$this->assertEquals($webhook['data']['ip'], '127.0.0.1');
|
||||
$this->assertNotEmpty($webhook['data']['osCode']);
|
||||
$this->assertIsString($webhook['data']['osCode']);
|
||||
$this->assertNotEmpty($webhook['data']['osName']);
|
||||
$this->assertIsString($webhook['data']['osName']);
|
||||
$this->assertNotEmpty($webhook['data']['osVersion']);
|
||||
$this->assertIsString($webhook['data']['osVersion']);
|
||||
$this->assertEquals($webhook['data']['clientType'], 'browser');
|
||||
$this->assertEquals($webhook['data']['clientCode'], 'CH');
|
||||
$this->assertEquals($webhook['data']['clientName'], 'Chrome');
|
||||
$this->assertNotEmpty($webhook['data']['clientVersion']);
|
||||
$this->assertIsString($webhook['data']['clientVersion']);
|
||||
$this->assertNotEmpty($webhook['data']['clientEngine']);
|
||||
$this->assertIsString($webhook['data']['clientEngine']);
|
||||
$this->assertIsString($webhook['data']['clientEngineVersion']);
|
||||
$this->assertIsString($webhook['data']['deviceName']);
|
||||
$this->assertIsString($webhook['data']['deviceBrand']);
|
||||
$this->assertIsString($webhook['data']['deviceModel']);
|
||||
$this->assertIsString($webhook['data']['countryCode']);
|
||||
$this->assertIsString($webhook['data']['countryName']);
|
||||
$this->assertEquals($webhook['data']['current'], true);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateAccount
|
||||
*/
|
||||
public function testDeleteAccountSessions($data):array
|
||||
{
|
||||
$email = $data['email'] ?? '';
|
||||
$password = $data['password'] ?? '';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$accountSession = $this->client->call(Client::METHOD_POST, '/account/sessions', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
]);
|
||||
|
||||
$session = $this->client->parseCookie((string)$accountSession['headers']['set-cookie'])['a_session_'.$this->getProject()['$id']];
|
||||
|
||||
$this->assertEquals($accountSession['headers']['status-code'], 201);
|
||||
|
||||
$accountSession = $this->client->call(Client::METHOD_DELETE, '/account/sessions', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]));
|
||||
|
||||
$this->assertEquals($accountSession['headers']['status-code'], 204);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.sessions.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertEquals($webhook['data']['sum'], 2);
|
||||
$this->assertNotEmpty($webhook['data']['sessions'][1]['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['sessions'][1]['userId']);
|
||||
$this->assertIsInt($webhook['data']['sessions'][1]['expire']);
|
||||
$this->assertEquals($webhook['data']['sessions'][1]['ip'], '127.0.0.1');
|
||||
$this->assertNotEmpty($webhook['data']['sessions'][1]['osCode']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['osCode']);
|
||||
$this->assertNotEmpty($webhook['data']['sessions'][1]['osName']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['osName']);
|
||||
$this->assertNotEmpty($webhook['data']['sessions'][1]['osVersion']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['osVersion']);
|
||||
$this->assertEquals($webhook['data']['sessions'][1]['clientType'], 'browser');
|
||||
$this->assertEquals($webhook['data']['sessions'][1]['clientCode'], 'CH');
|
||||
$this->assertEquals($webhook['data']['sessions'][1]['clientName'], 'Chrome');
|
||||
$this->assertNotEmpty($webhook['data']['sessions'][1]['clientVersion']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['clientVersion']);
|
||||
$this->assertNotEmpty($webhook['data']['sessions'][1]['clientEngine']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['clientEngine']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['clientEngineVersion']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['deviceName']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['deviceBrand']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['deviceModel']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['countryCode']);
|
||||
$this->assertIsString($webhook['data']['sessions'][1]['countryName']);
|
||||
$this->assertEquals($webhook['data']['sessions'][1]['current'], true);
|
||||
|
||||
$accountSession = $this->client->call(Client::METHOD_POST, '/account/sessions', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
]);
|
||||
|
||||
$this->assertEquals($accountSession['headers']['status-code'], 201);
|
||||
|
||||
$sessionId = $accountSession['body']['$id'];
|
||||
$session = $this->client->parseCookie((string)$accountSession['headers']['set-cookie'])['a_session_'.$this->getProject()['$id']];
|
||||
|
||||
return array_merge($data, [
|
||||
'sessionId' => $sessionId,
|
||||
'session' => $session,
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testDeleteAccountSessions
|
||||
*/
|
||||
public function testUpdateAccountName($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$session = $data['session'] ?? '';
|
||||
$newName = 'New Name';
|
||||
|
||||
$account = $this->client->call(Client::METHOD_PATCH, '/account/name', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'name' => $newName
|
||||
]);
|
||||
|
||||
$this->assertEquals($account['headers']['status-code'], 200);
|
||||
$this->assertIsArray($account['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.update.name');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], $newName);
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 0);
|
||||
$this->assertEquals($webhook['data']['email'], $email);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testUpdateAccountName
|
||||
*/
|
||||
public function testUpdateAccountPassword($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$password = $data['password'] ?? '';
|
||||
$session = $data['session'] ?? '';
|
||||
|
||||
$account = $this->client->call(Client::METHOD_PATCH, '/account/password', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'password' => 'new-password',
|
||||
'oldPassword' => $password,
|
||||
]);
|
||||
|
||||
$this->assertEquals($account['headers']['status-code'], 200);
|
||||
$this->assertIsArray($account['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.update.password');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], 'New Name');
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 0);
|
||||
$this->assertEquals($webhook['data']['email'], $email);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
$data['password'] = 'new-password';
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testUpdateAccountPassword
|
||||
*/
|
||||
public function testUpdateAccountEmail($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$newEmail = uniqid().'new@localhost.test';
|
||||
$session = $data['session'] ?? '';
|
||||
|
||||
$account = $this->client->call(Client::METHOD_PATCH, '/account/email', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'email' => $newEmail,
|
||||
'password' => 'new-password',
|
||||
]);
|
||||
|
||||
$this->assertEquals($account['headers']['status-code'], 200);
|
||||
$this->assertIsArray($account['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.update.email');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], 'New Name');
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 0);
|
||||
$this->assertEquals($webhook['data']['email'], $newEmail);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
$data['email'] = $newEmail;
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testUpdateAccountEmail
|
||||
*/
|
||||
public function testUpdateAccountPrefs($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$session = $data['session'] ?? '';
|
||||
|
||||
$account = $this->client->call(Client::METHOD_PATCH, '/account/prefs', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'prefs' => [
|
||||
'prefKey1' => 'prefValue1',
|
||||
'prefKey2' => 'prefValue2',
|
||||
]
|
||||
]);
|
||||
|
||||
$this->assertEquals($account['headers']['status-code'], 200);
|
||||
$this->assertIsArray($account['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.update.prefs');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], 'New Name');
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 0);
|
||||
$this->assertEquals($webhook['data']['email'], $email);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], [
|
||||
'prefKey1' => 'prefValue1',
|
||||
'prefKey2' => 'prefValue2',
|
||||
]);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testUpdateAccountPrefs
|
||||
*/
|
||||
public function testCreateAccountRecovery($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$session = $data['session'] ?? '';
|
||||
|
||||
$recovery = $this->client->call(Client::METHOD_POST, '/account/recovery', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'email' => $email,
|
||||
'url' => 'http://localhost/recovery',
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $recovery['headers']['status-code']);
|
||||
$this->assertIsArray($recovery['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.recovery.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id']), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertNotEmpty($webhook['data']['secret']);
|
||||
$this->assertIsNumeric($webhook['data']['expire']);
|
||||
|
||||
$data['secret'] = $webhook['data']['secret'];
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateAccountRecovery
|
||||
*/
|
||||
public function testUpdateAccountRecovery($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$session = $data['session'] ?? '';
|
||||
$secret = $data['secret'] ?? '';
|
||||
$password = 'newPassowrd2';
|
||||
|
||||
$recovery = $this->client->call(Client::METHOD_PUT, '/account/recovery', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'userId' => $id,
|
||||
'secret' => $secret,
|
||||
'password' => $password,
|
||||
'passwordAgain' => $password,
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $recovery['headers']['status-code']);
|
||||
$this->assertIsArray($recovery['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.recovery.update');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id']), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertNotEmpty($webhook['data']['secret']);
|
||||
$this->assertIsNumeric($webhook['data']['expire']);
|
||||
|
||||
$data['secret'] = $webhook['data']['secret'];
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testUpdateAccountPrefs
|
||||
*/
|
||||
public function testCreateAccountVerification($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$session = $data['session'] ?? '';
|
||||
|
||||
$verification = $this->client->call(Client::METHOD_POST, '/account/verification', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'url' => 'http://localhost/verification',
|
||||
]);
|
||||
|
||||
$this->assertEquals(201, $verification['headers']['status-code']);
|
||||
$this->assertIsArray($verification['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.verification.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertNotEmpty($webhook['data']['secret']);
|
||||
$this->assertIsNumeric($webhook['data']['expire']);
|
||||
|
||||
$data['secret'] = $webhook['data']['secret'];
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateAccountVerification
|
||||
*/
|
||||
public function testUpdateAccountVerification($data): array
|
||||
{
|
||||
$id = $data['id'] ?? '';
|
||||
$email = $data['email'] ?? '';
|
||||
$session = $data['session'] ?? '';
|
||||
$secret = $data['secret'] ?? '';
|
||||
|
||||
$verification = $this->client->call(Client::METHOD_PUT, '/account/verification', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'cookie' => 'a_session_'.$this->getProject()['$id'].'=' . $session,
|
||||
]), [
|
||||
'userId' => $id,
|
||||
'secret' => $secret,
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $verification['headers']['status-code']);
|
||||
$this->assertIsArray($verification['body']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'account.verification.update');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertNotEmpty($webhook['data']['secret']);
|
||||
$this->assertIsNumeric($webhook['data']['expire']);
|
||||
|
||||
$data['secret'] = $webhook['data']['secret'];
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateTeamMembership
|
||||
*/
|
||||
public function testUpdateTeamMembership($data): array
|
||||
{
|
||||
$teamUid = $data['teamId'] ?? '';
|
||||
$secret = $data['secret'] ?? '';
|
||||
$inviteUid = $data['inviteId'] ?? '';
|
||||
$userUid = $data['userId'] ?? '';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$team = $this->client->call(Client::METHOD_PATCH, '/teams/'.$teamUid.'/memberships/'.$inviteUid.'/status', array_merge([
|
||||
'origin' => 'http://localhost',
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
]), [
|
||||
'secret' => $secret,
|
||||
'userId' => $userUid,
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $team['headers']['status-code']);
|
||||
$this->assertNotEmpty($team['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'teams.memberships.update.status');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertNotEmpty($webhook['data']['userId']);
|
||||
$this->assertNotEmpty($webhook['data']['teamId']);
|
||||
$this->assertCount(2, $webhook['data']['roles']);
|
||||
$this->assertIsInt($webhook['data']['joined']);
|
||||
$this->assertEquals(true, $webhook['data']['confirm']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return [];
|
||||
}
|
||||
}
|
264
tests/e2e/Services/Webhooks/WebhooksCustomServerTest.php
Normal file
264
tests/e2e/Services/Webhooks/WebhooksCustomServerTest.php
Normal file
|
@ -0,0 +1,264 @@
|
|||
<?php
|
||||
|
||||
namespace Tests\E2E\Services\Webhooks;
|
||||
|
||||
use Tests\E2E\Client;
|
||||
use Tests\E2E\Scopes\ProjectCustom;
|
||||
use Tests\E2E\Scopes\Scope;
|
||||
use Tests\E2E\Scopes\SideServer;
|
||||
|
||||
class WebhooksCustomServerTest extends Scope
|
||||
{
|
||||
use WebhooksBase;
|
||||
use ProjectCustom;
|
||||
use SideServer;
|
||||
|
||||
/**
|
||||
* @depends testCreateCollection
|
||||
*/
|
||||
public function testUpdateCollection($data): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$actors = $this->client->call(Client::METHOD_PUT, '/database/collections/'.$data['actorsId'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'x-appwrite-key' => $this->getProject()['apiKey']
|
||||
]), [
|
||||
'name' => 'Actors1',
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
'rules' => [
|
||||
[
|
||||
'label' => 'First Name',
|
||||
'key' => 'firstName',
|
||||
'type' => 'text',
|
||||
'default' => '',
|
||||
'required' => true,
|
||||
'array' => false
|
||||
],
|
||||
[
|
||||
'label' => 'Last Name',
|
||||
'key' => 'lastName',
|
||||
'type' => 'text',
|
||||
'default' => '',
|
||||
'required' => true,
|
||||
'array' => false
|
||||
],
|
||||
],
|
||||
]);
|
||||
|
||||
$this->assertEquals($actors['headers']['status-code'], 200);
|
||||
$this->assertNotEmpty($actors['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'database.collections.update');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], 'Actors1');
|
||||
$this->assertIsArray($webhook['data']['$permissions']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['read']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['read']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(2, $webhook['data']['rules']);
|
||||
|
||||
return array_merge(['actorsId' => $actors['body']['$id']]);
|
||||
}
|
||||
|
||||
public function testDeleteCollection(): array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$actors = $this->client->call(Client::METHOD_POST, '/database/collections', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'x-appwrite-key' => $this->getProject()['apiKey']
|
||||
]), [
|
||||
'name' => 'Demo',
|
||||
'read' => ['*'],
|
||||
'write' => ['*'],
|
||||
'rules' => [
|
||||
[
|
||||
'label' => 'First Name',
|
||||
'key' => 'firstName',
|
||||
'type' => 'text',
|
||||
'default' => '',
|
||||
'required' => true,
|
||||
'array' => false
|
||||
],
|
||||
[
|
||||
'label' => 'Last Name',
|
||||
'key' => 'lastName',
|
||||
'type' => 'text',
|
||||
'default' => '',
|
||||
'required' => true,
|
||||
'array' => false
|
||||
],
|
||||
],
|
||||
]);
|
||||
|
||||
$this->assertEquals($actors['headers']['status-code'], 201);
|
||||
$this->assertNotEmpty($actors['body']['$id']);
|
||||
|
||||
$actors = $this->client->call(Client::METHOD_DELETE, '/database/collections/'.$actors['body']['$id'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
'x-appwrite-key' => $this->getProject()['apiKey']
|
||||
]), []);
|
||||
|
||||
$this->assertEquals($actors['headers']['status-code'], 204);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'database.collections.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), true);
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], 'Demo');
|
||||
$this->assertIsArray($webhook['data']['$permissions']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['read']);
|
||||
$this->assertIsArray($webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['read']);
|
||||
$this->assertCount(1, $webhook['data']['$permissions']['write']);
|
||||
$this->assertCount(2, $webhook['data']['rules']);
|
||||
|
||||
return [];
|
||||
}
|
||||
|
||||
public function testCreateUser():array
|
||||
{
|
||||
$email = uniqid().'user@localhost.test';
|
||||
$password = 'password';
|
||||
$name = 'User Name';
|
||||
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$user = $this->client->call(Client::METHOD_POST, '/users', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'email' => $email,
|
||||
'password' => $password,
|
||||
'name' => $name,
|
||||
]);
|
||||
|
||||
$this->assertEquals($user['headers']['status-code'], 201);
|
||||
$this->assertNotEmpty($user['body']['$id']);
|
||||
|
||||
$id = $user['body']['$id'];
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'users.create');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], $name);
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 0);
|
||||
$this->assertEquals($webhook['data']['email'], $email);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
return ['userId' => $user['body']['$id'], 'name' => $user['body']['name'], 'email' => $user['body']['email']];
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testCreateUser
|
||||
*/
|
||||
public function testUpdateUserStatus(array $data):array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$user = $this->client->call(Client::METHOD_PATCH, '/users/' . $data['userId'] . '/status', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'status' => 2,
|
||||
]);
|
||||
|
||||
$this->assertEquals($user['headers']['status-code'], 200);
|
||||
$this->assertNotEmpty($user['body']['$id']);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'users.update.status');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], $data['name']);
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 2);
|
||||
$this->assertEquals($webhook['data']['email'], $data['email']);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @depends testUpdateUserStatus
|
||||
*/
|
||||
public function testDeleteUser(array $data):array
|
||||
{
|
||||
/**
|
||||
* Test for SUCCESS
|
||||
*/
|
||||
$user = $this->client->call(Client::METHOD_DELETE, '/users/' . $data['userId'], array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()));
|
||||
|
||||
$this->assertEquals($user['headers']['status-code'], 204);
|
||||
|
||||
$webhook = $this->getLastRequest();
|
||||
|
||||
$this->assertEquals($webhook['method'], 'POST');
|
||||
$this->assertEquals($webhook['headers']['Content-Type'], 'application/json');
|
||||
$this->assertEquals($webhook['headers']['User-Agent'], 'Appwrite-Server vdev. Please report abuse at security@appwrite.io');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Event'], 'users.delete');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Signature'], 'not-yet-implemented');
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Id'] ?? '', $this->getProject()['webhookId']);
|
||||
$this->assertEquals($webhook['headers']['X-Appwrite-Webhook-Project-Id'] ?? '', $this->getProject()['$id']);
|
||||
$this->assertEquals(empty($webhook['headers']['X-Appwrite-Webhook-User-Id'] ?? ''), ('server' === $this->getSide()));
|
||||
$this->assertNotEmpty($webhook['data']['$id']);
|
||||
$this->assertEquals($webhook['data']['name'], $data['name']);
|
||||
$this->assertIsInt($webhook['data']['registration']);
|
||||
$this->assertEquals($webhook['data']['status'], 2);
|
||||
$this->assertEquals($webhook['data']['email'], $data['email']);
|
||||
$this->assertEquals($webhook['data']['emailVerification'], false);
|
||||
$this->assertEquals($webhook['data']['prefs'], []);
|
||||
|
||||
return $data;
|
||||
}
|
||||
}
|
|
@ -147,6 +147,5 @@ class WebhooksTest extends Scope
|
|||
$this->assertEquals($webhook['data']['name'], $name);
|
||||
$this->assertIsBool($webhook['data']['emailVerification']);
|
||||
$this->assertIsArray($webhook['data']['prefs']);
|
||||
$this->assertIsArray($webhook['data']['roles']);
|
||||
}
|
||||
}
|
|
@ -79,5 +79,12 @@ class AuthorizationTest extends TestCase
|
|||
|
||||
$this->assertEquals($this->object->isValid($this->document->getPermissions()), false);
|
||||
|
||||
Authorization::setRole('textX');
|
||||
|
||||
$this->assertContains('textX', Authorization::getRoles());
|
||||
|
||||
Authorization::unsetRole('textX');
|
||||
|
||||
$this->assertNotContains('textX', Authorization::getRoles());
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue