Merge pull request #3798 from appwrite/matej-qa-3
Fix: 1.0 bugs from QA (3)
This commit is contained in:
commit
b98bbf482a
8 changed files with 49 additions and 121 deletions
|
@ -10,6 +10,7 @@
|
|||
- Queries have been improved to allow even more flexibility, and introduced to new endpoints. See the Queries V2 section in the document for more information [#3702](https://github.com/appwrite/appwrite/pull/3702)
|
||||
- Compound indexes are now more flexible [#151](https://github.com/utopia-php/database/pull/151)
|
||||
- `createExecution` parameter `async` default value was changed from `true` to `false` [#3781](https://github.com/appwrite/appwrite/pull/3781)
|
||||
- String attribute `status` has been refactored to a Boolean attribute `enabled` in the functions collection [#3798](https://github.com/appwrite/appwrite/pull/3798)
|
||||
- `time` attribute in Execution response model has been reanamed to `duration` to be more consistent with other response models. [#3801](https://github.com/appwrite/appwrite/pull/3801)
|
||||
|
||||
## Features
|
||||
|
|
|
@ -2084,15 +2084,14 @@ $collections = [
|
|||
'filters' => [],
|
||||
],
|
||||
[
|
||||
'array' => false,
|
||||
'$id' => ID::custom('status'),
|
||||
'type' => Database::VAR_STRING,
|
||||
'format' => '',
|
||||
'size' => Database::LENGTH_KEY,
|
||||
'$id' => ID::custom('enabled'),
|
||||
'type' => Database::VAR_BOOLEAN,
|
||||
'signed' => true,
|
||||
'required' => false,
|
||||
'default' => null,
|
||||
'size' => 0,
|
||||
'format' => '',
|
||||
'filters' => [],
|
||||
'required' => true,
|
||||
'array' => false,
|
||||
],
|
||||
[
|
||||
'$id' => ID::custom('runtime'),
|
||||
|
@ -2210,10 +2209,10 @@ $collections = [
|
|||
'orders' => [Database::ORDER_ASC],
|
||||
],
|
||||
[
|
||||
'$id' => ID::custom('_key_status'),
|
||||
'$id' => ID::custom('_key_enabled'),
|
||||
'type' => Database::INDEX_KEY,
|
||||
'attributes' => ['status'],
|
||||
'lengths' => [Database::LENGTH_KEY],
|
||||
'attributes' => ['enabled'],
|
||||
'lengths' => [],
|
||||
'orders' => [Database::ORDER_ASC],
|
||||
],
|
||||
[
|
||||
|
|
|
@ -67,16 +67,17 @@ App::post('/v1/functions')
|
|||
->param('events', [], new ArrayList(new ValidatorEvent(), APP_LIMIT_ARRAY_PARAMS_SIZE), 'Events list. Maximum of ' . APP_LIMIT_ARRAY_PARAMS_SIZE . ' events are allowed.', true)
|
||||
->param('schedule', '', new Cron(), 'Schedule CRON syntax.', true)
|
||||
->param('timeout', 15, new Range(1, (int) App::getEnv('_APP_FUNCTIONS_TIMEOUT', 900)), 'Function maximum execution time in seconds.', true)
|
||||
->param('enabled', true, new Boolean(), 'Is function enabled?', true)
|
||||
->inject('response')
|
||||
->inject('dbForProject')
|
||||
->inject('events')
|
||||
->action(function (string $functionId, string $name, array $execute, string $runtime, array $events, string $schedule, int $timeout, Response $response, Database $dbForProject, Event $eventsInstance) {
|
||||
->action(function (string $functionId, string $name, array $execute, string $runtime, array $events, string $schedule, int $timeout, bool $enabled, Response $response, Database $dbForProject, Event $eventsInstance) {
|
||||
|
||||
$functionId = ($functionId == 'unique()') ? ID::unique() : $functionId;
|
||||
$function = $dbForProject->createDocument('functions', new Document([
|
||||
'$id' => $functionId,
|
||||
'execute' => $execute,
|
||||
'status' => 'disabled',
|
||||
'enabled' => $enabled,
|
||||
'name' => $name,
|
||||
'runtime' => $runtime,
|
||||
'deployment' => '',
|
||||
|
@ -424,12 +425,13 @@ App::put('/v1/functions/:functionId')
|
|||
->param('events', [], new ArrayList(new ValidatorEvent(), APP_LIMIT_ARRAY_PARAMS_SIZE), 'Events list. Maximum of ' . APP_LIMIT_ARRAY_PARAMS_SIZE . ' events are allowed.', true)
|
||||
->param('schedule', '', new Cron(), 'Schedule CRON syntax.', true)
|
||||
->param('timeout', 15, new Range(1, (int) App::getEnv('_APP_FUNCTIONS_TIMEOUT', 900)), 'Maximum execution time in seconds.', true)
|
||||
->param('enabled', true, new Boolean(), 'Is function enabled?', true)
|
||||
->inject('response')
|
||||
->inject('dbForProject')
|
||||
->inject('project')
|
||||
->inject('user')
|
||||
->inject('events')
|
||||
->action(function (string $functionId, string $name, array $execute, array $events, string $schedule, int $timeout, Response $response, Database $dbForProject, Document $project, Document $user, Event $eventsInstance) {
|
||||
->action(function (string $functionId, string $name, array $execute, array $events, string $schedule, int $timeout, bool $enabled, Response $response, Database $dbForProject, Document $project, Document $user, Event $eventsInstance) {
|
||||
|
||||
$function = $dbForProject->getDocument('functions', $functionId);
|
||||
|
||||
|
@ -441,6 +443,8 @@ App::put('/v1/functions/:functionId')
|
|||
$cron = (!empty($function->getAttribute('deployment')) && !empty($schedule)) ? new CronExpression($schedule) : null;
|
||||
$next = (!empty($function->getAttribute('deployment')) && !empty($schedule)) ? DateTime::format($cron->getNextRunDate()) : null;
|
||||
|
||||
$enabled ??= $function->getAttribute('enabled', true);
|
||||
|
||||
$function = $dbForProject->updateDocument('functions', $function->getId(), new Document(array_merge($function->getArrayCopy(), [
|
||||
'execute' => $execute,
|
||||
'name' => $name,
|
||||
|
@ -448,6 +452,7 @@ App::put('/v1/functions/:functionId')
|
|||
'schedule' => $schedule,
|
||||
'scheduleNext' => $next,
|
||||
'timeout' => $timeout,
|
||||
'enabled' => $enabled,
|
||||
'search' => implode(' ', [$functionId, $name, $function->getAttribute('runtime')]),
|
||||
])));
|
||||
|
||||
|
@ -945,13 +950,16 @@ App::post('/v1/functions/:functionId/executions')
|
|||
->inject('user')
|
||||
->inject('events')
|
||||
->inject('usage')
|
||||
->action(function (string $functionId, string $data, bool $async, Response $response, Document $project, Database $dbForProject, Document $user, Event $events, Stats $usage) {
|
||||
->inject('mode')
|
||||
->action(function (string $functionId, string $data, bool $async, Response $response, Document $project, Database $dbForProject, Document $user, Event $events, Stats $usage, string $mode) {
|
||||
|
||||
$function = Authorization::skip(fn () => $dbForProject->getDocument('functions', $functionId));
|
||||
|
||||
if ($function->isEmpty()) {
|
||||
if ($function->isEmpty() || !$function->getAttribute('enabled')) {
|
||||
if (!($mode === APP_MODE_ADMIN && Auth::isPrivilegedUser(Authorization::getRoles()))) {
|
||||
throw new Exception(Exception::FUNCTION_NOT_FOUND);
|
||||
}
|
||||
}
|
||||
|
||||
$runtimes = Config::getParam('runtimes', []);
|
||||
|
||||
|
@ -1137,13 +1145,16 @@ App::get('/v1/functions/:functionId/executions')
|
|||
->param('search', '', new Text(256), 'Search term to filter your list results. Max length: 256 chars.', true)
|
||||
->inject('response')
|
||||
->inject('dbForProject')
|
||||
->action(function (string $functionId, array $queries, string $search, Response $response, Database $dbForProject) {
|
||||
->inject('mode')
|
||||
->action(function (string $functionId, array $queries, string $search, Response $response, Database $dbForProject, string $mode) {
|
||||
|
||||
$function = Authorization::skip(fn () => $dbForProject->getDocument('functions', $functionId));
|
||||
|
||||
if ($function->isEmpty()) {
|
||||
if ($function->isEmpty() || !$function->getAttribute('enabled')) {
|
||||
if (!($mode === APP_MODE_ADMIN && Auth::isPrivilegedUser(Authorization::getRoles()))) {
|
||||
throw new Exception(Exception::FUNCTION_NOT_FOUND);
|
||||
}
|
||||
}
|
||||
|
||||
$queries = Query::parseQueries($queries);
|
||||
|
||||
|
@ -1206,13 +1217,16 @@ App::get('/v1/functions/:functionId/executions/:executionId')
|
|||
->param('executionId', '', new UID(), 'Execution ID.')
|
||||
->inject('response')
|
||||
->inject('dbForProject')
|
||||
->action(function (string $functionId, string $executionId, Response $response, Database $dbForProject) {
|
||||
->inject('mode')
|
||||
->action(function (string $functionId, string $executionId, Response $response, Database $dbForProject, string $mode) {
|
||||
|
||||
$function = Authorization::skip(fn () => $dbForProject->getDocument('functions', $functionId));
|
||||
|
||||
if ($function->isEmpty()) {
|
||||
if ($function->isEmpty() || !$function->getAttribute('enabled')) {
|
||||
if (!($mode === APP_MODE_ADMIN && Auth::isPrivilegedUser(Authorization::getRoles()))) {
|
||||
throw new Exception(Exception::FUNCTION_NOT_FOUND);
|
||||
}
|
||||
}
|
||||
|
||||
$execution = $dbForProject->getDocument('executions', $executionId);
|
||||
|
||||
|
@ -1359,43 +1373,18 @@ App::get('/v1/functions/:functionId/variables')
|
|||
->label('sdk.response.type', Response::CONTENT_TYPE_JSON)
|
||||
->label('sdk.response.model', Response::MODEL_VARIABLE_LIST)
|
||||
->param('functionId', null, new UID(), 'Function unique ID.', false)
|
||||
->param('queries', [], new Variables(), 'Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/databases#querying-documents). Maximum of ' . APP_LIMIT_ARRAY_PARAMS_SIZE . ' queries are allowed, each ' . APP_LIMIT_ARRAY_ELEMENT_SIZE . ' characters long. You may filter on the following attributes: ' . implode(', ', Variables::ALLOWED_ATTRIBUTES), true)
|
||||
->param('search', '', new Text(256), 'Search term to filter your list results. Max length: 256 chars.', true)
|
||||
->inject('response')
|
||||
->inject('dbForProject')
|
||||
->action(function (string $functionId, array $queries, string $search, Response $response, Database $dbForProject) {
|
||||
->action(function (string $functionId, Response $response, Database $dbForProject) {
|
||||
$function = $dbForProject->getDocument('functions', $functionId);
|
||||
|
||||
if ($function->isEmpty()) {
|
||||
throw new Exception(Exception::FUNCTION_NOT_FOUND);
|
||||
}
|
||||
|
||||
$queries = Query::parseQueries($queries);
|
||||
|
||||
if (!empty($search)) {
|
||||
$queries[] = Query::search('search', $search);
|
||||
}
|
||||
|
||||
// Get cursor document if there was a cursor query
|
||||
$cursor = Query::getByType($queries, Query::TYPE_CURSORAFTER, Query::TYPE_CURSORBEFORE);
|
||||
$cursor = reset($cursor);
|
||||
if ($cursor) {
|
||||
/** @var Query $cursor */
|
||||
$variableId = $cursor->getValue();
|
||||
$cursorDocument = $dbForProject->getDocument('variables', $variableId);
|
||||
|
||||
if ($cursorDocument->isEmpty()) {
|
||||
throw new Exception(Exception::GENERAL_CURSOR_NOT_FOUND, "Variable '{$variableId}' for the 'cursor' value not found.");
|
||||
}
|
||||
|
||||
$cursor->setValue($cursorDocument);
|
||||
}
|
||||
|
||||
$filterQueries = Query::groupByType($queries)['filters'];
|
||||
|
||||
$response->dynamic(new Document([
|
||||
'variables' => $dbForProject->find('variables', $queries),
|
||||
'total' => $dbForProject->count('variables', $filterQueries, APP_LIMIT_COUNT),
|
||||
'variables' => $function->getAttribute('vars'),
|
||||
'total' => \count($function->getAttribute('vars')),
|
||||
]), Response::MODEL_VARIABLE_LIST);
|
||||
});
|
||||
|
||||
|
|
|
@ -523,8 +523,6 @@ sort($patterns);
|
|||
data-service="functions.listVariables"
|
||||
data-event="load,project.update,functions.createVariable,functions.updateVariable,functions.deleteVariable"
|
||||
data-name="function-variables"
|
||||
data-param-queries="limit(100)"
|
||||
data-param-queries-cast-to="array" data-param-queries-cast-from="csv"
|
||||
data-param-function-id="{{router.params.id}}"
|
||||
data-scope="sdk">Variables</h2>
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ class Functions extends Base
|
|||
{
|
||||
public const ALLOWED_ATTRIBUTES = [
|
||||
'name',
|
||||
'status',
|
||||
'enabled',
|
||||
'runtime',
|
||||
'deployment',
|
||||
'schedule',
|
||||
|
|
|
@ -43,11 +43,11 @@ class Func extends Model
|
|||
'default' => '',
|
||||
'example' => 'My Function',
|
||||
])
|
||||
->addRule('status', [
|
||||
'type' => self::TYPE_STRING,
|
||||
'description' => 'Function status. Possible values: `disabled`, `enabled`',
|
||||
'default' => '',
|
||||
'example' => 'enabled',
|
||||
->addRule('enabled', [
|
||||
'type' => self::TYPE_BOOLEAN,
|
||||
'description' => 'Function enabled.',
|
||||
'default' => true,
|
||||
'example' => false,
|
||||
])
|
||||
->addRule('runtime', [
|
||||
'type' => self::TYPE_STRING,
|
||||
|
|
|
@ -182,74 +182,14 @@ class FunctionsConsoleClientTest extends Scope
|
|||
|
||||
$this->assertEquals(200, $response['headers']['status-code']);
|
||||
$this->assertEquals(1, sizeof($response['body']['variables']));
|
||||
$this->assertEquals(1, $response['body']['total']);
|
||||
$this->assertEquals("APP_TEST", $response['body']['variables'][0]['key']);
|
||||
$this->assertEquals("TESTINGVALUE", $response['body']['variables'][0]['value']);
|
||||
|
||||
$variableId = $response['body']['variables'][0]['$id'];
|
||||
|
||||
$response = $this->client->call(Client::METHOD_GET, '/functions/' . $data['functionId'] . '/variables', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'queries' => [ 'limit(0)' ]
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $response['headers']['status-code']);
|
||||
$this->assertCount(0, $response['body']['variables']);
|
||||
|
||||
$response = $this->client->call(Client::METHOD_GET, '/functions/' . $data['functionId'] . '/variables', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'queries' => [ 'offset(1)' ]
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $response['headers']['status-code']);
|
||||
$this->assertCount(0, $response['body']['variables']);
|
||||
|
||||
$response = $this->client->call(Client::METHOD_GET, '/functions/' . $data['functionId'] . '/variables', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'queries' => [ 'equal("key", "APP_TEST")' ]
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $response['headers']['status-code']);
|
||||
$this->assertCount(1, $response['body']['variables']);
|
||||
|
||||
$response = $this->client->call(Client::METHOD_GET, '/functions/' . $data['functionId'] . '/variables', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'search' => $variableId
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $response['headers']['status-code']);
|
||||
$this->assertCount(1, $response['body']['variables']);
|
||||
|
||||
$response = $this->client->call(Client::METHOD_GET, '/functions/' . $data['functionId'] . '/variables', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'queries' => [ 'equal("key", "NON_EXISTING_VARIABLE")' ]
|
||||
]);
|
||||
|
||||
$this->assertEquals(200, $response['headers']['status-code']);
|
||||
$this->assertCount(0, $response['body']['variables']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
*/
|
||||
|
||||
$response = $this->client->call(Client::METHOD_GET, '/functions/' . $data['functionId'] . '/variables', array_merge([
|
||||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'queries' => [ 'equal("value", "MY_SECRET")' ]
|
||||
]);
|
||||
|
||||
$this->assertEquals(400, $response['headers']['status-code']);
|
||||
|
||||
return $data;
|
||||
}
|
||||
|
||||
|
@ -403,6 +343,7 @@ class FunctionsConsoleClientTest extends Scope
|
|||
|
||||
$this->assertEquals(200, $response['headers']['status-code']);
|
||||
$this->assertEquals(0, sizeof($response['body']['variables']));
|
||||
$this->assertEquals(0, $response['body']['total']);
|
||||
|
||||
/**
|
||||
* Test for FAILURE
|
||||
|
|
|
@ -140,7 +140,7 @@ class FunctionsCustomServerTest extends Scope
|
|||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'queries' => [ 'equal("status", "disabled")' ]
|
||||
'queries' => [ 'equal("enabled", true)' ]
|
||||
]);
|
||||
|
||||
$this->assertEquals($response['headers']['status-code'], 200);
|
||||
|
@ -150,7 +150,7 @@ class FunctionsCustomServerTest extends Scope
|
|||
'content-type' => 'application/json',
|
||||
'x-appwrite-project' => $this->getProject()['$id'],
|
||||
], $this->getHeaders()), [
|
||||
'queries' => [ 'equal("status", "enabled")' ]
|
||||
'queries' => [ 'equal("enabled", false)' ]
|
||||
]);
|
||||
|
||||
$this->assertEquals($response['headers']['status-code'], 200);
|
||||
|
|
Loading…
Reference in a new issue