Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,12 @@
# Change Log

## 19.4.0

* Add `getScreenshot` method to `Avatars` service
* Add enums `Theme`, `Output` and `Timezone`
* Update runtime enums to add support for `dart39` and `flutter335` runtimes
* Fix passing of `null` values and stripping only non-nullable optional parameters from the request body

## 19.3.0

* Add `total` parameter to list queries allowing skipping counting rows in a table for improved performance
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ Add this to your package's `pubspec.yaml` file:

```yml
dependencies:
dart_appwrite: ^19.3.0
dart_appwrite: ^19.4.0
```
You can install packages from the command line:
Expand Down
31 changes: 31 additions & 0 deletions docs/examples/avatars/get-screenshot.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import 'package:dart_appwrite/dart_appwrite.dart';

Client client = Client()
.setEndpoint('https://<REGION>.cloud.appwrite.io/v1') // Your API Endpoint
.setProject('<YOUR_PROJECT_ID>') // Your project ID
.setSession(''); // The user session to authenticate with

Avatars avatars = Avatars(client);

UInt8List result = await avatars.getScreenshot(
Copy link

@coderabbitai coderabbitai bot Nov 13, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

Fix the type name.

The return type should be Uint8List (lowercase 'i'), not UInt8List.

Apply this diff:

-UInt8List result = await avatars.getScreenshot(
+Uint8List result = await avatars.getScreenshot(
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
UInt8List result = await avatars.getScreenshot(
Uint8List result = await avatars.getScreenshot(
🤖 Prompt for AI Agents
In docs/examples/avatars/get-screenshot.md around line 10, the type name is
incorrect: change the return type from "UInt8List" to "Uint8List" (lowercase
'i') so the example uses the correct Dart type; update that occurrence
accordingly.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Fetch details about the SDK generator PR
gh pr view 1253 --repo appwrite/sdk-generator --json title,body,state,url

Length of output: 133


@ChiragAgg5k, perfect! I can see you've already created PR #1253 to fix the typo at the generator level. This is exactly the right approach—fixing it at the source ensures all generated SDKs will have the correct Uint8List spelling going forward.

Once that PR is merged and you regenerate this SDK, the typo will be automatically corrected. Thanks for addressing this! 🎯

url: 'https://example.com',
headers: {}, // (optional)
viewportWidth: 1, // (optional)
viewportHeight: 1, // (optional)
scale: 0.1, // (optional)
theme: .light, // (optional)
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

Add the enum qualifier.

The theme parameter should be qualified with the enum name, e.g., Theme.light instead of .light.

Apply this diff:

-    theme: .light, // (optional)
+    theme: Theme.light, // (optional)
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
theme: .light, // (optional)
theme: Theme.light, // (optional)
🤖 Prompt for AI Agents
In docs/examples/avatars/get-screenshot.md around line 16, the theme parameter
uses an unqualified enum value ".light"; replace it with the fully-qualified
enum member (e.g., Theme.light) so the example compiles and reads correctly;
update the line to use Theme.light and ensure any other enum usages in this
snippet are similarly qualified.

userAgent: '<USER_AGENT>', // (optional)
fullpage: false, // (optional)
locale: '<LOCALE>', // (optional)
timezone: .africaAbidjan, // (optional)
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

Add the enum qualifier.

The timezone parameter should be qualified with the enum name, e.g., Timezone.africaAbidjan instead of .africaAbidjan.

Apply this diff:

-    timezone: .africaAbidjan, // (optional)
+    timezone: Timezone.africaAbidjan, // (optional)
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
timezone: .africaAbidjan, // (optional)
timezone: Timezone.africaAbidjan, // (optional)
🤖 Prompt for AI Agents
In docs/examples/avatars/get-screenshot.md around line 20, the timezone enum
value is used without its qualifier; replace the unqualified `.africaAbidjan`
with the fully qualified enum `Timezone.africaAbidjan` (and ensure the Timezone
enum is imported or available in this example context if required).

latitude: -90, // (optional)
longitude: -180, // (optional)
accuracy: 0, // (optional)
touch: false, // (optional)
permissions: [], // (optional)
sleep: 0, // (optional)
width: 0, // (optional)
height: 0, // (optional)
quality: -1, // (optional)
output: .jpg, // (optional)
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

Add the enum qualifier.

The output parameter should be qualified with the enum name, e.g., Output.jpg instead of .jpg.

Apply this diff:

-    output: .jpg, // (optional)
+    output: Output.jpg, // (optional)
🤖 Prompt for AI Agents
In docs/examples/avatars/get-screenshot.md around line 30, the example sets
output: .jpg but must use the enum qualifier; change the value to Output.jpg (or
the correct enum namespace used in this project) so the example reads output:
Output.jpg, and if the enum is in a different module ensure the example
references it correctly (add the proper import or namespace prefix as used
elsewhere).

);
3 changes: 3 additions & 0 deletions lib/enums.dart
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@ part 'src/enums/o_auth_provider.dart';
part 'src/enums/browser.dart';
part 'src/enums/credit_card.dart';
part 'src/enums/flag.dart';
part 'src/enums/theme.dart';
part 'src/enums/timezone.dart';
part 'src/enums/output.dart';
part 'src/enums/relationship_type.dart';
part 'src/enums/relation_mutate.dart';
part 'src/enums/index_type.dart';
Expand Down
24 changes: 12 additions & 12 deletions lib/services/account.dart
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ class Account extends Service {
'userId': userId,
'email': email,
'password': password,
'name': name,
if (name != null) 'name': name,
};

final Map<String, String> apiHeaders = {
Expand Down Expand Up @@ -82,8 +82,8 @@ class Account extends Service {
final String apiPath = '/account/identities';

final Map<String, dynamic> apiParams = {
'queries': queries,
'total': total,
if (queries != null) 'queries': queries,
if (total != null) 'total': total,
};

final Map<String, String> apiHeaders = {};
Expand Down Expand Up @@ -137,8 +137,8 @@ class Account extends Service {
final String apiPath = '/account/logs';

final Map<String, dynamic> apiParams = {
'queries': queries,
'total': total,
if (queries != null) 'queries': queries,
if (total != null) 'total': total,
};

final Map<String, String> apiHeaders = {};
Expand Down Expand Up @@ -562,7 +562,7 @@ class Account extends Service {

final Map<String, dynamic> apiParams = {
'password': password,
'oldPassword': oldPassword,
if (oldPassword != null) 'oldPassword': oldPassword,
};

final Map<String, String> apiHeaders = {
Expand Down Expand Up @@ -936,7 +936,7 @@ class Account extends Service {
final Map<String, dynamic> apiParams = {
'userId': userId,
'email': email,
'phrase': phrase,
if (phrase != null) 'phrase': phrase,
};

final Map<String, String> apiHeaders = {
Expand Down Expand Up @@ -973,8 +973,8 @@ class Account extends Service {
final Map<String, dynamic> apiParams = {
'userId': userId,
'email': email,
'url': url,
'phrase': phrase,
if (url != null) 'url': url,
if (phrase != null) 'phrase': phrase,
};

final Map<String, String> apiHeaders = {
Expand Down Expand Up @@ -1010,9 +1010,9 @@ class Account extends Service {
.replaceAll('{provider}', provider.value);

final Map<String, dynamic> params = {
'success': success,
'failure': failure,
'scopes': scopes,
if (success != null) 'success': success,
if (failure != null) 'failure': failure,
if (scopes != null) 'scopes': scopes,
'project': client.config['project'],
};

Expand Down
99 changes: 81 additions & 18 deletions lib/services/avatars.dart
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,9 @@ class Avatars extends Service {
'/avatars/browsers/{code}'.replaceAll('{code}', code.value);

final Map<String, dynamic> params = {
'width': width,
'height': height,
'quality': quality,
if (width != null) 'width': width,
if (height != null) 'height': height,
if (quality != null) 'quality': quality,
'project': client.config['project'],
'session': client.config['session'],
};
Expand Down Expand Up @@ -54,9 +54,9 @@ class Avatars extends Service {
'/avatars/credit-cards/{code}'.replaceAll('{code}', code.value);

final Map<String, dynamic> params = {
'width': width,
'height': height,
'quality': quality,
if (width != null) 'width': width,
if (height != null) 'height': height,
if (quality != null) 'quality': quality,
'project': client.config['project'],
'session': client.config['session'],
};
Expand Down Expand Up @@ -100,9 +100,9 @@ class Avatars extends Service {
'/avatars/flags/{code}'.replaceAll('{code}', code.value);

final Map<String, dynamic> params = {
'width': width,
'height': height,
'quality': quality,
if (width != null) 'width': width,
if (height != null) 'height': height,
if (quality != null) 'quality': quality,
'project': client.config['project'],
'session': client.config['session'],
};
Expand All @@ -129,8 +129,8 @@ class Avatars extends Service {

final Map<String, dynamic> params = {
'url': url,
'width': width,
'height': height,
if (width != null) 'width': width,
if (height != null) 'height': height,
'project': client.config['project'],
'session': client.config['session'],
};
Expand Down Expand Up @@ -161,10 +161,10 @@ class Avatars extends Service {
final String apiPath = '/avatars/initials';

final Map<String, dynamic> params = {
'name': name,
'width': width,
'height': height,
'background': background,
if (name != null) 'name': name,
if (width != null) 'width': width,
if (height != null) 'height': height,
if (background != null) 'background': background,
'project': client.config['project'],
'session': client.config['session'],
};
Expand All @@ -183,9 +183,72 @@ class Avatars extends Service {

final Map<String, dynamic> params = {
'text': text,
'size': size,
'margin': margin,
'download': download,
if (size != null) 'size': size,
if (margin != null) 'margin': margin,
if (download != null) 'download': download,
'project': client.config['project'],
'session': client.config['session'],
};

final res = await client.call(HttpMethod.get,
path: apiPath, params: params, responseType: ResponseType.bytes);
return res.data;
}

/// Use this endpoint to capture a screenshot of any website URL. This endpoint
/// uses a headless browser to render the webpage and capture it as an image.
///
/// You can configure the browser viewport size, theme, user agent,
/// geolocation, permissions, and more. Capture either just the viewport or the
/// full page scroll.
///
/// When width and height are specified, the image is resized accordingly. If
/// both dimensions are 0, the API provides an image at original size. If
/// dimensions are not specified, the default viewport size is 1280x720px.
Future<Uint8List> getScreenshot(
{required String url,
Map? headers,
int? viewportWidth,
int? viewportHeight,
double? scale,
enums.Theme? theme,
String? userAgent,
bool? fullpage,
String? locale,
enums.Timezone? timezone,
double? latitude,
double? longitude,
double? accuracy,
bool? touch,
List<String>? permissions,
int? sleep,
int? width,
int? height,
int? quality,
enums.Output? output}) async {
final String apiPath = '/avatars/screenshots';

final Map<String, dynamic> params = {
'url': url,
if (headers != null) 'headers': headers,
if (viewportWidth != null) 'viewportWidth': viewportWidth,
if (viewportHeight != null) 'viewportHeight': viewportHeight,
if (scale != null) 'scale': scale,
if (theme != null) 'theme': theme!.value,
if (userAgent != null) 'userAgent': userAgent,
if (fullpage != null) 'fullpage': fullpage,
if (locale != null) 'locale': locale,
if (timezone != null) 'timezone': timezone!.value,
if (latitude != null) 'latitude': latitude,
if (longitude != null) 'longitude': longitude,
if (accuracy != null) 'accuracy': accuracy,
if (touch != null) 'touch': touch,
if (permissions != null) 'permissions': permissions,
if (sleep != null) 'sleep': sleep,
if (width != null) 'width': width,
if (height != null) 'height': height,
if (quality != null) 'quality': quality,
if (output != null) 'output': output!.value,
'project': client.config['project'],
'session': client.config['session'],
};
Expand Down
Loading