diff --git a/src/partials/account-vs-user.md b/src/partials/account-vs-user.md
new file mode 100644
index 0000000000..638d806300
--- /dev/null
+++ b/src/partials/account-vs-user.md
@@ -0,0 +1,21 @@
+
+{% info title="Account vs Users API" %}
+Appwrite provides two APIs to manager user accounts.
+
+The Account API is the API you should use in your **client applications** like web, Flutter, mobile, and native apps.
+Account API creates sessions, which represent an authenticated user and is attached to a user's [account](/docs/products/auth/account).
+Sessions respect [permissions](/docs/advanced/platform/permissions), which means users can only access resources if they have been granted the correct permissions.
+
+You'll notice that the Account API doesn't allow you to view or make changes to other users.
+This is by design and for **security reasons**.
+
+[Account API references](/docs/references/cloud/client-web/account)
+
+The Users API is a dedicated API for managing users from an admin's perspective. **Do not use the Users API on client applications**.
+It should be used with backend or server-side applications with the [Server SDK](#).
+
+Users API uses API keys instead of sessions.
+This means they're not resticted by permissions, but by the scopes granted to the API key used.
+
+[Users API references](/docs/references/cloud/server-nodejs/users)
+{% /info %}
\ No newline at end of file
diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte
index 1804869c0e..a2306a3695 100644
--- a/src/routes/+layout.svelte
+++ b/src/routes/+layout.svelte
@@ -9,6 +9,7 @@
import '@fontsource/inter/800.css';
import '@fontsource/inter/900.css';
import '$scss/index.scss';
+ import '@appwrite.io/pink-icons';
diff --git a/src/routes/+page.svelte b/src/routes/+page.svelte
index 0fef7c07c8..df79675f9f 100644
--- a/src/routes/+page.svelte
+++ b/src/routes/+page.svelte
@@ -6,7 +6,9 @@
import { Tabs } from '$lib/UI';
import PreFooter from '$lib/components/PreFooter.svelte';
import OpenSource from '$lib/animations/OpenSource.svelte';
- import Products from '$lib/animations/Products.svelte';
+ import Products from '$lib/animations/Products/Products.svelte';
+ import ProductsMobile from '$lib/animations/Products/ProductsMobile.svelte';
+ import { Spline } from '$lib/components';
+
+
+
+
+
+
+
+
+
+
+```
+{% /tabsitem %}
+
+{% tabsitem #linux title="Linux" %}
+
+Add your app **name** and **package name**.
+Your package name is generally the **name** in your [pubspec.yaml](https://github.com/appwrite/playground-for-flutter/blob/master/pubspec.yaml#L1) file.
+If you cannot find the correct package name, run the application in Linux and make any request with proper exception handling.
+You should get the application ID needed to add in the received error message.
+
+{% /tabsitem %}
+
+{% tabsitem #macos title="macOS" %}
+
+Add your app **name** and **Bundle ID**. You can find your **Bundle Identifier** in the **General** tab for your app's primary target in XCode.
+
+The Appwrite SDK uses `ASWebAuthenticationSession` on macOS 10.15+ to allow OAuth authentication. You have to change your macOS **Deployment Target** in XCode to be macOS >= 10.15 to be able to build your app for macOS.
+
+In order to capture the Appwrite OAuth 2 callback url, the following URL scheme needs to added to your `Info.plist`.
+
+```xml
+CFBundleURLTypes
+
+
+ CFBundleTypeRole
+ Editor
+ CFBundleURLName
+ io.appwrite
+ CFBundleURLSchemes
+
+ appwrite-callback-[PROJECT_ID]
+
+
+
+```
+{% /tabsitem %}
+
+{% tabsitem #windows title="Windows" %}
+
+For **Windows**, add your app *name* and *package name*.
+Your package name is generally the **name** in your [pubspec.yaml](https://github.com/appwrite/playground-for-flutter/blob/master/pubspec.yaml#L1) file.
+If you cannot find the correct package name, run the application in Windows, and make any request with proper exception handling. You should get the application ID needed to add in the received error message.
+{% /tabsitem %}
+
+{% /tabs %}
+
+
+
+You can skip optional steps.
+
+{% /section %}
+{% section #step-2 step=2 title="Create Flutter project" %}
+Create a Flutter project.
+
+```sh
+flutter create my_app && cd my_app
+```
+{% /section %}
+
+{% section #step-3 step=3 title="Install Appwrite" %}
+Install the Appwrite SDK for Flutter.
+
+```sh
+flutter pub add appwrite
+```
+
+{% /section %}
+
+{% section #step-4 step=4 title="Import Appwrite" %}
+Find your project's ID in the **Settings** page.
+
+
+
+Create a new file `lib/appwrite.dart` and add the following code to it, replace `` with your project ID.
+
+```dart
+import 'package:appwrite/appwrite.dart';
+
+class Appwrite {
+ static final Appwrite instance = Appwrite._internal();
+
+ late final Client client;
+ late final Account account;
+ factory Appwrite._() {
+ return instance;
+ }
+
+ Appwrite._internal() {
+ client = Client()
+ .setEndpoint("https://cloud.appwrite.io/v1")
+ .setProject("");
+ account = Account(client);
+ }
+}
+```
+{% /section %}
+{% section #step-5 step=5 title="Create a login page" %}
+Add the following code to `src/App.jsx`.
+import 'package:appwrite/appwrite.dart';
+
+```dart
+import 'package:flutter/material.dart';
+import 'package:appwrite/appwrite.dart';
+import 'package:appwrite/models.dart' as models;
+
+import 'package:my_app/appwrite.dart';
+
+void main() {
+ runApp(MyApp());
+}
+
+class MyApp extends StatelessWidget {
+ @override
+ Widget build(BuildContext context) {
+ return MaterialApp(
+ home: Scaffold(
+ appBar: AppBar(title: const Text('My App')),
+ body: Padding(
+ padding: const EdgeInsets.all(16.0),
+ child: MyForm(),
+ ),
+ ),
+ );
+ }
+}
+
+class MyForm extends StatefulWidget {
+ @override
+ MyFormState createState() {
+ return MyFormState();
+ }
+}
+
+class MyFormState extends State {
+ models.User? loggedInUser;
+ final TextEditingController emailController = TextEditingController();
+ final TextEditingController passwordController = TextEditingController();
+ final TextEditingController nameController = TextEditingController();
+
+ Future login(String email, String password) async {
+ await Appwrite.instance.account
+ .createEmailSession(email: email, password: password);
+ final user = await Appwrite.instance.account.get();
+ setState(() {
+ loggedInUser = user;
+ });
+ }
+
+ Future register(String email, String password, String name) async {
+ await Appwrite.instance.account.create(
+ userId: ID.unique(), email: email, password: password, name: name);
+ await login(email, password);
+ }
+
+ Future logout() async {
+ await Appwrite.instance.account.deleteSession(sessionId: 'current');
+ setState(() {
+ loggedInUser = null;
+ });
+ }
+
+ @override
+ Widget build(BuildContext context) {
+ return Column(
+ crossAxisAlignment: CrossAxisAlignment.start,
+ children: [
+ Text(loggedInUser != null
+ ? 'Logged in as ${loggedInUser!.name}'
+ : 'Not logged in'),
+ SizedBox(height: 16.0),
+ TextField(
+ controller: emailController,
+ decoration: InputDecoration(labelText: 'Email'),
+ ),
+ SizedBox(height: 16.0),
+ TextField(
+ controller: passwordController,
+ decoration: InputDecoration(labelText: 'Password'),
+ obscureText: true,
+ ),
+ SizedBox(height: 16.0),
+ TextField(
+ controller: nameController,
+ decoration: InputDecoration(labelText: 'Name'),
+ ),
+ SizedBox(height: 16.0),
+ ElevatedButton(
+ onPressed: () {
+ login(emailController.text, passwordController.text);
+ },
+ child: Text('Login'),
+ ),
+ ElevatedButton(
+ onPressed: () {
+ register(emailController.text, passwordController.text,
+ nameController.text);
+ },
+ child: Text('Register'),
+ ),
+ ElevatedButton(
+ onPressed: () {
+ logout();
+ },
+ child: Text('Logout'),
+ ),
+ ],
+ );
+ }
+}
+```
+{% /section %}
+
+{% section #step-6 step=6 title="Checkout what you've built" %}
+Run your project with `flutter run` and select a browser, platform, or emulator to run your project.
+{% /section %}
\ No newline at end of file
diff --git a/src/routes/docs/quick-starts/react/+page.markdoc b/src/routes/docs/quick-starts/react/+page.markdoc
index cd35a56637..9859409d62 100644
--- a/src/routes/docs/quick-starts/react/+page.markdoc
+++ b/src/routes/docs/quick-starts/react/+page.markdoc
@@ -14,7 +14,7 @@ Head to the [Appwrite Console](https://cloud.appwrite.io/console).
If this is your first time using Appwrite, create an accout and create your first project.
-Then, under **Add a platform**, add a **Web app**. The **Hostname** should be localhost.
+Then, under **Add a platform**, add a **Web app**. The **Hostname** should be `localhost`.

@@ -59,55 +59,64 @@ export { ID } from 'appwrite';
{% section #step-5 step=5 title="Create a login page" %}
Add the following code to `src/App.jsx`.
-```html
-
-
-
- {{ loggedInUser ? `Logged in as ${loggedInUser.name}` : 'Not logged in' }}
-
-
-
-
-
-
-
+export default App;
```
{% /section %}
{% section #step-6 step=6 title="Checkout what you've built" %}
-Run your project with `npm run dev` and open [http://localhost:3000](http://localhost:3000) in your browser.
+Run your project with `npm run dev -- --open --port 3000` and open [http://localhost:3000](http://localhost:3000) in your browser.
{% /section %}
\ No newline at end of file
diff --git a/src/routes/docs/quick-starts/sveltekit/+page.markdoc b/src/routes/docs/quick-starts/sveltekit/+page.markdoc
index d767b33166..2208fab870 100644
--- a/src/routes/docs/quick-starts/sveltekit/+page.markdoc
+++ b/src/routes/docs/quick-starts/sveltekit/+page.markdoc
@@ -11,7 +11,7 @@ Head to the [Appwrite Console](https://cloud.appwrite.io/console).
If this is your first time using Appwrite, create an accout and create your first project.
-Then, under **Add a platform**, add a **Web app**. The **Hostname** should be localhost.
+Then, under **Add a platform**, add a **Web app**. The **Hostname** should be `localhost`.

@@ -100,7 +100,7 @@ Create a new file `src/routes/index.svelte` and add the following code to it.
{% /section %}
{% section #step-6 step=6 title="Checkout what you've built" %}
-Run your project with `npm run dev` and open [http://localhost:3000](http://localhost:3000) in your browser.
+Run your project with `npm run dev -- --open --port 3000` and open [http://localhost:3000](http://localhost:3000) in your browser.
{% /section %}
diff --git a/src/routes/docs/quick-starts/vuejs/+page.markdoc b/src/routes/docs/quick-starts/vuejs/+page.markdoc
index 39da5bfe12..5c8bf345c9 100644
--- a/src/routes/docs/quick-starts/vuejs/+page.markdoc
+++ b/src/routes/docs/quick-starts/vuejs/+page.markdoc
@@ -14,7 +14,7 @@ Head to the [Appwrite Console](https://cloud.appwrite.io/console).
If this is your first time using Appwrite, create an accout and create your first project.
-Then, under **Add a platform**, add a **Web app**. The **Hostname** should be localhost.
+Then, under **Add a platform**, add a **Web app**. The **Hostname** should be `localhost`.

@@ -109,5 +109,5 @@ const logout = async () => {
{% /section %}
{% section #step-6 step=6 title="Checkout what you've built" %}
-Run your project with `npm run dev` and open [http://localhost:3000](http://localhost:3000) in your browser.
+Run your project with `npm run dev -- --open --port 3000` and open [http://localhost:3000](http://localhost:3000) in your browser.
{% /section %}
diff --git a/src/routes/docs/references/+page.svelte b/src/routes/docs/references/+page.svelte
index b3a425249b..049f67759c 100644
--- a/src/routes/docs/references/+page.svelte
+++ b/src/routes/docs/references/+page.svelte
@@ -1 +1,5 @@
-placeholder
\ No newline at end of file
+
+
+placeholder
diff --git a/src/routes/docs/references/+layout.svelte b/src/routes/docs/references/Layout.svelte
similarity index 95%
rename from src/routes/docs/references/+layout.svelte
rename to src/routes/docs/references/Layout.svelte
index 5bbfbe54c9..65bd07f068 100644
--- a/src/routes/docs/references/+layout.svelte
+++ b/src/routes/docs/references/Layout.svelte
@@ -4,7 +4,8 @@
import Sidebar, { type NavParent, type NavTree } from '$lib/layouts/Sidebar.svelte';
import { preferredPlatform, preferredVersion } from '$lib/utils/references';
- $: expandable = $page.url.pathname.startsWith('/docs/references/');
+ export let expandable = false;
+
$: prefix = `/docs/references/${$preferredVersion ?? $page.params?.version ?? 'cloud'}/${
$preferredPlatform ?? $page.params?.platform ?? 'client-web'
}`;
diff --git a/src/routes/docs/references/[version]/[platform]/[service]/+layout.svelte b/src/routes/docs/references/[version]/[platform]/[service]/+layout.svelte
new file mode 100644
index 0000000000..c72730eac7
--- /dev/null
+++ b/src/routes/docs/references/[version]/[platform]/[service]/+layout.svelte
@@ -0,0 +1,7 @@
+
+
+
+
+
diff --git a/src/routes/docs/references/[version]/[platform]/[service]/+page.svelte b/src/routes/docs/references/[version]/[platform]/[service]/+page.svelte
index ac5545dc85..6475e58ae0 100644
--- a/src/routes/docs/references/[version]/[platform]/[service]/+page.svelte
+++ b/src/routes/docs/references/[version]/[platform]/[service]/+page.svelte
@@ -181,19 +181,30 @@
+ Example
+
+
+
diff --git a/src/routes/docs/sdks/+page.markdoc b/src/routes/docs/sdks/+page.markdoc
index 2a225437f6..298b39bf20 100644
--- a/src/routes/docs/sdks/+page.markdoc
+++ b/src/routes/docs/sdks/+page.markdoc
@@ -13,7 +13,7 @@ We're always working on improving and extending the current stack of available p
Client libraries for integrating with Appwrite to build client-based applications and websites. Read one of the many [quick starts](/docs/quick-starts) guides for your framework of choice to start building your first application.
{% table %}
-* {% width=80 %}
+* {% width=48 %}
* Platform
* GitHub Repository
* {% width=80 %}
@@ -48,7 +48,7 @@ Client libraries for integrating with Appwrite to build client-based application
Server libraries for integrating with Appwrite to build server side integrations or use inside your [Appwrite Functions](/docs/products/functions). Read one of the many [quick starts](/docs/quick-starts) guides for your language/runtime of choice to start building your first server integration.
{% table %}
-* {% width=80 %}
+* {% width=48 %}
* Platform
* GitHub Repository
* {% width=80 %}
diff --git a/src/routes/docs/tutorials/react/+layout.svelte b/src/routes/docs/tutorials/react/+layout.svelte
new file mode 100644
index 0000000000..fb9fb3980f
--- /dev/null
+++ b/src/routes/docs/tutorials/react/+layout.svelte
@@ -0,0 +1,10 @@
+
+
+
diff --git a/src/routes/docs/tutorials/react/+layout.ts b/src/routes/docs/tutorials/react/+layout.ts
new file mode 100644
index 0000000000..562b11506f
--- /dev/null
+++ b/src/routes/docs/tutorials/react/+layout.ts
@@ -0,0 +1,11 @@
+import type { LayoutLoad } from './$types';
+
+export const load: LayoutLoad = ({ url }) => {
+ const tutorials = import.meta.glob('./**/*.markdoc', {
+ eager: true
+ });
+ return {
+ tutorials,
+ pathname: url.pathname
+ };
+};
diff --git a/src/routes/docs/tutorials/react/+page.ts b/src/routes/docs/tutorials/react/+page.ts
new file mode 100644
index 0000000000..c026e98b75
--- /dev/null
+++ b/src/routes/docs/tutorials/react/+page.ts
@@ -0,0 +1,6 @@
+import { redirect } from '@sveltejs/kit';
+import type { PageLoad } from './$types';
+
+export const load: PageLoad = async () => {
+ throw redirect(303, '/docs/tutorials/react/step-1');
+};
diff --git a/src/routes/docs/tutorials/react/step-1/+page.markdoc b/src/routes/docs/tutorials/react/step-1/+page.markdoc
new file mode 100644
index 0000000000..3a46e1177d
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-1/+page.markdoc
@@ -0,0 +1,31 @@
+---
+layout: tutorial
+title: Introduction
+description: This is the description used for SEO.
+step: 1
+difficulty: easy
+readtime: 10
+---
+
+**Idea Tracker**: an app to track all the side project ideas that you'll start, but probably never finish.
+In this tutorial, you will build Idea Tracker with Appwrite and React.
+
+[TODO: Image]
+
+You can follow along with a fresh repo or [clone the project on GitHub](#).
+
+## Concepts {% #concepts %}
+
+This tutorial will introduce the following concepts:
+
+1. Setting up your first project
+2. Authentication
+3. Databases and collections
+4. Queries and pagination
+5. Storage
+
+
+## Prerequisites {% #prerequisites %}
+
+1. Basic knowledge of JavaScript and React.
+2. Have [Node.js](#) and [NPM](#) installed on your computer
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/react/step-2/+page.markdoc b/src/routes/docs/tutorials/react/step-2/+page.markdoc
new file mode 100644
index 0000000000..d166dfceb0
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-2/+page.markdoc
@@ -0,0 +1,28 @@
+---
+layout: tutorial
+title: Create app
+description: This is the description used for SEO.
+step: 2
+---
+
+## Create React project {% #create-react-project %}
+
+Create a React app with the `npm create` command.
+
+```sh
+npm create vite@latest --template react ideas-tracker && cd ideas-tracker
+```
+
+## Add dependencies {% #add-dependencies %}
+
+Install the JavaScript Appwrite SDK.
+
+```sh
+npm install appwrite
+```
+
+You can start the development server to watch your app update in the browser as you make changes.
+
+```sh
+npm run dev -- --open --port 3000
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/react/step-3/+page.markdoc b/src/routes/docs/tutorials/react/step-3/+page.markdoc
new file mode 100644
index 0000000000..50c9fa0f4c
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-3/+page.markdoc
@@ -0,0 +1,42 @@
+---
+layout: tutorial
+title: Set up Appwrite
+description: This is the description used for SEO.
+step: 3
+---
+
+## Create project {% #create-project %}
+
+Head to the [Appwrite Console](https://cloud.appwrite.io/console).
+
+
+
+If this is your first time using Appwrite, create an account and create your first project.
+
+Then, under **Add a platform**, add a **Web app**. The **Hostname** should be localhost.
+
+
+
+You can skip optional steps.
+
+## Initialize Appwrite SDK {% #init-sdk %}
+
+To use Appwrite in our Svelte app, we'll need to find our project ID. Find your project's ID in the **Settings** page.
+
+
+
+Create a new file `src/lib/appwrite.js` to hold our Appwrite related code.
+Only one instance of the `Client()` class should be created per app.
+Add the following code to it, replacing `` with your project ID.
+
+```js
+import { Client } from "appwrite";
+
+const client = new Client();
+client
+ .setEndpoint("https://cloud.appwrite.io/v1")
+ .setProject(""); // Replace with your project IDxw
+
+export const account = new Account(client);
+export const database = new Database(client);
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/react/step-4/+page.markdoc b/src/routes/docs/tutorials/react/step-4/+page.markdoc
new file mode 100644
index 0000000000..5551c802b2
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-4/+page.markdoc
@@ -0,0 +1,185 @@
+---
+layout: tutorial
+title: Add authentication
+description: This is the description used for SEO.
+step: 4
+---
+
+## User context
+
+In React, you can use [context](https://reactjs.org/docs/context.html) to share data between components.
+We'll use context and a custom hook to manage our user's data.
+
+Create a new file `src/lib/context/user.jsx` and add the following code to it.
+
+```js
+import { createContext, useContext, useEffect, useState } from "react";
+import { account } from "../appwrite";
+
+const UserContext = createContext();
+
+export function useUser() {
+ return useContext(UserContext);
+}
+
+export function UserProvider(props) {
+ const [user, setUser] = useState(null);
+
+ async function login(email, password) {
+ const loggedIn = await account.createEmailSession(email, password);
+ setUser(loggedIn);
+ }
+
+ async function logout() {
+ await account.deleteSession("current");
+ setUser(null);
+ }
+
+ async function register(email, password) {
+ await account.create(email, password);
+ await login(email, password);
+ }
+
+ async function init() {
+ try {
+ const loggedIn = await account.get();
+ setUser(loggedIn);
+ } catch (err) {
+ setUser(null);
+ }
+ }
+
+ useEffect(() => {
+ init();
+ }, []);
+
+ return (
+
+ {props.children}
+
+ );
+}
+```
+
+Now, we can use the `useUser` hook to access the user's data from any component. However, we first need to wrap our app with the `UserProvider`.
+
+## Basic routing
+
+First, wrap the `main` element with the `UserProvider` component.
+
+Update `src/App.jsx` to the following code.
+
+```jsx
+import { Home } from "./pages/Home";
+import { UserProvider } from "./lib/context/user";
+
+function App() {
+ const isLoginPage = window.location.pathname === "/login";
+
+ return (
+
+
+ Home page
+
+
+ );
+}
+
+export default App;
+```
+
+Then, optionally render the `Login` component if the path is `/login`, otherwise render the `Home` component.
+
+Update `src/App.jsx` to the following code.
+
+```jsx
+import { Login } from "./pages/Login";
+import { Home } from "./pages/Home";
+import { UserProvider } from "./lib/context/user";
+
+function App() {
+ const isLoginPage = window.location.pathname === "/login";
+
+ return (
+
+
+ {isLoginPage ? : }
+
+
+ );
+}
+
+export default App;
+```
+
+## Home page
+
+Create a new file `src/pages/Home.jsx` and add the following stub code to it.
+
+```jsx
+// We'll complete this component later
+export function Home() {
+ return (
+
I'm the home page
+ );
+}
+```
+
+## Login page
+
+Finally, we are able to create the login page. Users will be able to login or register from this page, so we'll need to add two buttons.
+
+Create a new file `src/pages/Login.jsx` and add the following code to it.
+
+```jsx
+import { useState } from "react";
+import { useUser } from "../lib/context/user";
+
+export function Login() {
+ const user = useUser();
+
+ const [email, setEmail] = useState("");
+ const [password, setPassword] = useState("");
+
+ return (
+
+
Login or register
+
+
+ );
+}
+```
+
diff --git a/src/routes/docs/tutorials/react/step-5/+page.markdoc b/src/routes/docs/tutorials/react/step-5/+page.markdoc
new file mode 100644
index 0000000000..709163abc2
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-5/+page.markdoc
@@ -0,0 +1,57 @@
+---
+layout: tutorial
+title: Add navigation
+description: This is the description used for SEO.
+step: 5
+difficulty: easy
+readtime: 10
+---
+
+In our app we want to have a navigation bar that is always visible. We will add it to the `App` component and use the `useUser` hook to show either:
+- a logout button if the user is logged in.
+- a login button if the user is not logged in.
+
+Update the App componenent in `src/App.jsx`:
+
+```jsx
+import { Login } from "./pages/Login";
+import { Home } from "./pages/Home";
+import { UserProvider, useUser } from "./lib/context/user";
+
+function App() {
+ const isLoginPage = window.location.pathname === "/login";
+
+ return (
+
+
+ {/* Add the navbar before page content */}
+ {isLoginPage ? : }
+
+
+ );
+}
+
+function Navbar() {
+ const user = useUser();
+
+ return (
+
+ );
+}
+
+export default App;
+```
diff --git a/src/routes/docs/tutorials/react/step-6/+page.markdoc b/src/routes/docs/tutorials/react/step-6/+page.markdoc
new file mode 100644
index 0000000000..fc1783ea81
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-6/+page.markdoc
@@ -0,0 +1,79 @@
+---
+layout: tutorial
+title: Add database
+description: This is the description used for SEO.
+step: 6
+difficulty: easy
+readtime: 10
+---
+## Create collection
+In Appwrite, data is stored as a collection of documents. Create a collection in the [Appwrite Console](https://cloud.appwrite.io/) to store our ideas.
+
+
+
+Create a new collection with the following attributes:
+| Field | Type | Required |
+|-------------|--------|----------|
+| userId | String | Yes |
+| title | String | Yes |
+| description | String | No |
+
+## Ideas context
+
+Now that you have a collection to hold ideas, we can read and write to it from our app. Like we did with the user data, we will create a React context to hold our ideas.
+Create a new file `src/lib/context/ideas.jsx` and add the following code to it.
+
+```js
+import { createContext, useContext, useEffect, useState } from "react";
+import { databases } from "../appwrite";
+import { ID, Query } from "appwrite";
+
+export const IDEAS_DATABASE_ID = ""; // Replace with your database ID
+export const IDEAS_COLLECTION_ID = ""; // Replace with your collection ID
+
+const IdeasContext = createContext();
+
+export function useIdeas() {
+ return useContext(IdeasContext);
+}
+
+export function IdeasProvider(props) {
+ const [ideas, setIdeas] = useState([]);
+
+ async function add(idea) {
+ const response = await databases.createDocument(
+ IDEAS_DATABASE_ID,
+ IDEAS_COLLECTION_ID,
+ ID.unique(),
+ idea
+ );
+ setIdeas((ideas) => [response.$id, ...ideas].slice(0, 10));
+ }
+
+ async function remove(id) {
+ await databases.deleteDocument(IDEAS_DATABASE_ID, IDEAS_COLLECTION_ID, id);
+ setIdeas((ideas) => ideas.filter((idea) => idea.$id !== id));
+ await init(); // Refetch ideas to ensure we have 10 items
+ }
+
+ async function init() {
+ const response = await databases.listDocuments(
+ IDEAS_DATABASE_ID,
+ IDEAS_COLLECTION_ID,
+ [Query.orderDesc("$createdAt"), Query.limit(10)]
+ );
+ setIdeas(response.documents);
+ }
+
+ useEffect(() => {
+ init();
+ }, []);
+
+ return (
+
+ {props.children}
+
+ );
+}
+```
+
diff --git a/src/routes/docs/tutorials/react/step-7/+page.markdoc b/src/routes/docs/tutorials/react/step-7/+page.markdoc
new file mode 100644
index 0000000000..fa6db81157
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-7/+page.markdoc
@@ -0,0 +1,83 @@
+---
+layout: tutorial
+title: Create ideas page
+description: This is the description used for SEO.
+step: 7
+difficulty: easy
+readtime: 10
+---
+
+Using the `useIdeas` hook we can now display the ideas on the page. We will also add a form to submit new ideas.
+
+Overwrite the contents of `src/pages/Home.jsx` with the following:
+
+```jsx
+import { useState } from "react";
+import { useUser } from "../lib/context/user";
+import { useIdeas } from "../lib/context/ideas";
+
+export function Home() {
+ const user = useUser();
+ const ideas = useIdeas();
+
+ const [title, setTitle] = useState("");
+ const [description, setDescription] = useState("");
+
+ return (
+ <>
+ {/* Show the submit form to logged in users. */}
+ {user.current ? (
+
+
Submit Idea
+
+
+ ) : (
+
+
Please login to submit an idea.
+
+ )}
+
+
Latest Ideas
+
+ {ideas.current.map((idea) => (
+
+ {idea.title}
+
{idea.description}
+ {/* Show the remove button to idea owner. */}
+ {user.current && user.current.$id === idea.userId && (
+
+ )}
+
+ ))}
+
+
+ >
+ );
+}
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/react/step-8/+page.markdoc b/src/routes/docs/tutorials/react/step-8/+page.markdoc
new file mode 100644
index 0000000000..9c5af3c44c
--- /dev/null
+++ b/src/routes/docs/tutorials/react/step-8/+page.markdoc
@@ -0,0 +1,14 @@
+---
+layout: tutorial
+title: Next steps
+description: This is the description used for SEO.
+step: 8
+difficulty: easy
+readtime: 10
+---
+
+## Test your project {% #test-project %}
+Run your project with `npm run dev -- --open --port 3000` and open [http://localhost:3000](http://localhost:3000) in your browser.
+
+## Add style {% #add-style %}
+If you want to see a version of this project, complete with CSS styles, clone [this GitHub repository]().
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/+layout.svelte b/src/routes/docs/tutorials/sveltekit/+layout.svelte
new file mode 100644
index 0000000000..fb9fb3980f
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/+layout.svelte
@@ -0,0 +1,10 @@
+
+
+
diff --git a/src/routes/docs/tutorials/sveltekit/+layout.ts b/src/routes/docs/tutorials/sveltekit/+layout.ts
new file mode 100644
index 0000000000..562b11506f
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/+layout.ts
@@ -0,0 +1,11 @@
+import type { LayoutLoad } from './$types';
+
+export const load: LayoutLoad = ({ url }) => {
+ const tutorials = import.meta.glob('./**/*.markdoc', {
+ eager: true
+ });
+ return {
+ tutorials,
+ pathname: url.pathname
+ };
+};
diff --git a/src/routes/docs/tutorials/sveltekit/+page.ts b/src/routes/docs/tutorials/sveltekit/+page.ts
new file mode 100644
index 0000000000..d85840c6e1
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/+page.ts
@@ -0,0 +1,6 @@
+import { redirect } from '@sveltejs/kit';
+import type { PageLoad } from './$types';
+
+export const load: PageLoad = async () => {
+ throw redirect(303, '/docs/tutorials/sveltekit/step-1');
+};
diff --git a/src/routes/docs/tutorials/sveltekit/step-1/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-1/+page.markdoc
new file mode 100644
index 0000000000..7051ac9c3a
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-1/+page.markdoc
@@ -0,0 +1,28 @@
+---
+layout: tutorial
+title: Introduction
+description: This is the description used for SEO.
+step: 1
+difficulty: easy
+readtime: 10
+---
+
+**Idea Tracker**: an app to track all the side project ideas that you'll start, but probably never finish.
+In this tutorial, you will build Idea Tracker with Appwrite and SvelteKit.
+
+[TODO: Image]
+
+You can follow along with a fresh repo or [clone the project on GitHub](#).
+
+## Concepts {% #concepts %}
+This tutorial will introduce the following concepts:
+
+1. Setting up your first project
+2. Authentication
+3. Databases and collections
+4. Queries and pagination
+5. Storage
+
+## Prerequisites {% #prerequisites %}
+1. Basic knowledge of JavaScript and Svelte.
+2. Have [Node.js](#) and [NPM](#) installed on your computer
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/step-2/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-2/+page.markdoc
new file mode 100644
index 0000000000..e543c0ee46
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-2/+page.markdoc
@@ -0,0 +1,28 @@
+---
+layout: tutorial
+title: Create app
+description: This is the description used for SEO.
+step: 2
+---
+
+## Create SvelteKit project {% #create-sveltekit-project %}
+
+Create a SvelteKit app with the `npm create` command and select `Skeleton project`
+
+```sh
+npm create svelte@latest ideas-tracker && cd ideas-tracker
+```
+
+## Add dependencies {% #add-dependencies %}
+
+Install the JavaScript Appwrite SDK.
+
+```sh
+npm install appwrite
+```
+
+You can start the development server to watch your app update in the browser as you make changes.
+
+```sh
+npm run dev -- --open --port 3000
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/step-3/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-3/+page.markdoc
new file mode 100644
index 0000000000..50c9fa0f4c
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-3/+page.markdoc
@@ -0,0 +1,42 @@
+---
+layout: tutorial
+title: Set up Appwrite
+description: This is the description used for SEO.
+step: 3
+---
+
+## Create project {% #create-project %}
+
+Head to the [Appwrite Console](https://cloud.appwrite.io/console).
+
+
+
+If this is your first time using Appwrite, create an account and create your first project.
+
+Then, under **Add a platform**, add a **Web app**. The **Hostname** should be localhost.
+
+
+
+You can skip optional steps.
+
+## Initialize Appwrite SDK {% #init-sdk %}
+
+To use Appwrite in our Svelte app, we'll need to find our project ID. Find your project's ID in the **Settings** page.
+
+
+
+Create a new file `src/lib/appwrite.js` to hold our Appwrite related code.
+Only one instance of the `Client()` class should be created per app.
+Add the following code to it, replacing `` with your project ID.
+
+```js
+import { Client } from "appwrite";
+
+const client = new Client();
+client
+ .setEndpoint("https://cloud.appwrite.io/v1")
+ .setProject(""); // Replace with your project IDxw
+
+export const account = new Account(client);
+export const database = new Database(client);
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/step-4/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-4/+page.markdoc
new file mode 100644
index 0000000000..34f2680323
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-4/+page.markdoc
@@ -0,0 +1,89 @@
+---
+layout: tutorial
+title: Add authentication
+description: This is the description used for SEO.
+step: 4
+---
+
+## Using stores
+
+In Svelte, [stores](https://svelte.dev/docs/svelte-store) are a way to share state and changes between components.
+We'll use a store to keep track of our user's data.
+
+Create a new file `src/lib/stores/user.js` and add the following code to it.
+
+```js
+import { writable } from "svelte/store";
+import { ID } from "appwrite";
+import { goto } from "$app/navigation";
+import { account } from "$lib/appwrite";
+
+const store = writable(null);
+
+async function init() {
+ try {
+ store.set(await account.get());
+ } catch (e) {
+ store.set(null);
+ }
+}
+
+async function register(email, password) {
+ await account.create(ID.unique(), email, password);
+ await login(email, password);
+}
+
+async function login(email, password) {
+ await account.createEmailSession(email, password);
+ await init();
+ goto("/"); // Redirect to home page after login
+}
+
+async function logout() {
+ await account.deleteSession("current");
+ store.set(null);
+}
+
+// Expose the store's value with $user
+export const user = {
+ subscribe: store.subscribe,
+ register,
+ login,
+ logout,
+ init,
+};
+```
+
+## Login page
+
+Using this store, we can build a login page.
+
+Create a new file `src/routes/login/+page.svelte` and add the following code to it.
+
+```html
+
+
+
Login or register
+
+
+
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/step-5/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-5/+page.markdoc
new file mode 100644
index 0000000000..d2a653bb25
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-5/+page.markdoc
@@ -0,0 +1,57 @@
+---
+layout: tutorial
+title: Add navigation
+description: This is the description used for SEO.
+step: 5
+difficulty: easy
+readtime: 10
+---
+
+Create a layout component, used by all pages, to display a navbar. The navbar will show a login button if the user is not logged in, and a logout button if the user is logged in.
+
+In this component, we can call our `user.init()` function to check if the user is logged in when the page loads.
+
+Create a new file `src/routes/+layout.svelte` and add the following code to it.
+
+```html
+
+
+
+
+
+
+
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/step-6/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-6/+page.markdoc
new file mode 100644
index 0000000000..ea172c7f40
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-6/+page.markdoc
@@ -0,0 +1,74 @@
+---
+layout: tutorial
+title: Add database
+description: This is the description used for SEO.
+step: 6
+difficulty: easy
+readtime: 10
+---
+## Create collection
+In Appwrite, data is stored as a collection of documents. Create a collection in the [Appwrite Console](https://cloud.appwrite.io/) to store our ideas.
+
+
+
+Create a new collection with the following attributes:
+| Field | Type | Required |
+|-------------|--------|----------|
+| userId | String | Yes |
+| title | String | Yes |
+| description | String | No |
+
+## Add and remove methods
+Now that you have a collection to hold ideas, we can read and write to it from our app.
+Create a new file `src/lib/stores/ideas.js` and add the following code to it.
+
+```js
+import { writable } from "svelte/store";
+import { ID, Query } from "appwrite";
+import { databases } from "$lib/appwrite";
+
+export const IDEAS_DATABASE_ID = "6508783c5dc784d544dd"; // Replace with your database ID
+export const IDEAS_COLLECTION_ID = "65087840ab307cb06883"; // Replace with your collection ID
+
+const databases = new Databases(client);
+
+const store = writable([]);
+
+async function init() {
+ const response = await databases.listDocuments(
+ IDEAS_DATABASE_ID,
+ IDEAS_COLLECTION_ID,
+ // Use a query to how the latest ideas first
+ [Query.orderDesc("$createdAt")]
+ );
+ store.set(response.documents);
+}
+
+async function add(userId, title, description) {
+ const response = await databases.createDocument(
+ IDEAS_DATABASE_ID,
+ IDEAS_COLLECTION_ID,
+ ID.unique(),
+ {
+ userId,
+ title,
+ description,
+ }
+ );
+ store.update((ideas) => [response, ...ideas]);
+}
+
+async function remove(id) {
+ await databases.deleteDocument(IDEAS_DATABASE_ID, IDEAS_COLLECTION_ID, id);
+ store.update((ideas) => ideas.filter((idea) => idea.$id !== id));
+}
+
+export const ideas = {
+ subscribe: store.subscribe, // Expose the store's value with $ideas
+ init,
+ add,
+ remove,
+};
+```
+
+Remember to use a store to hold data returned from Appwrite Databases, so your components can be updated when the data changes.
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/step-7/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-7/+page.markdoc
new file mode 100644
index 0000000000..7276ee47e5
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-7/+page.markdoc
@@ -0,0 +1,82 @@
+---
+layout: tutorial
+title: Create ideas page
+description: This is the description used for SEO.
+step: 7
+difficulty: easy
+readtime: 10
+---
+
+Using the `ideas` store, we can build a page to submit and view ideas.
+
+Overwrite the contents of `src/routes/+page.svelte` with the following code.
+
+```html
+
+
+{#if $user}
+
+
+
+
+
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/sveltekit/step-8/+page.markdoc b/src/routes/docs/tutorials/sveltekit/step-8/+page.markdoc
new file mode 100644
index 0000000000..9c5af3c44c
--- /dev/null
+++ b/src/routes/docs/tutorials/sveltekit/step-8/+page.markdoc
@@ -0,0 +1,14 @@
+---
+layout: tutorial
+title: Next steps
+description: This is the description used for SEO.
+step: 8
+difficulty: easy
+readtime: 10
+---
+
+## Test your project {% #test-project %}
+Run your project with `npm run dev -- --open --port 3000` and open [http://localhost:3000](http://localhost:3000) in your browser.
+
+## Add style {% #add-style %}
+If you want to see a version of this project, complete with CSS styles, clone [this GitHub repository]().
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/vue/+layout.svelte b/src/routes/docs/tutorials/vue/+layout.svelte
new file mode 100644
index 0000000000..fb9fb3980f
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/+layout.svelte
@@ -0,0 +1,10 @@
+
+
+
diff --git a/src/routes/docs/tutorials/vue/+layout.ts b/src/routes/docs/tutorials/vue/+layout.ts
new file mode 100644
index 0000000000..562b11506f
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/+layout.ts
@@ -0,0 +1,11 @@
+import type { LayoutLoad } from './$types';
+
+export const load: LayoutLoad = ({ url }) => {
+ const tutorials = import.meta.glob('./**/*.markdoc', {
+ eager: true
+ });
+ return {
+ tutorials,
+ pathname: url.pathname
+ };
+};
diff --git a/src/routes/docs/tutorials/vue/+page.ts b/src/routes/docs/tutorials/vue/+page.ts
new file mode 100644
index 0000000000..2566839476
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/+page.ts
@@ -0,0 +1,6 @@
+import { redirect } from '@sveltejs/kit';
+import type { PageLoad } from './$types';
+
+export const load: PageLoad = async () => {
+ throw redirect(303, '/docs/tutorials/vue/step-1');
+};
diff --git a/src/routes/docs/tutorials/vue/step-1/+page.markdoc b/src/routes/docs/tutorials/vue/step-1/+page.markdoc
new file mode 100644
index 0000000000..2e577d4854
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-1/+page.markdoc
@@ -0,0 +1,31 @@
+---
+layout: tutorial
+title: Introduction
+description: This is the description used for SEO.
+step: 1
+difficulty: easy
+readtime: 10
+---
+
+**Idea Tracker**: an app to track all the side project ideas that you'll start, but probably never finish.
+In this tutorial, you will build Idea Tracker with Appwrite and Vue.
+
+[TODO: Image]
+
+You can follow along with a fresh repo or [clone the project on GitHub](#).
+
+## Concepts {% #concepts %}
+
+This tutorial will introduce the following concepts:
+
+1. Setting up your first project
+2. Authentication
+3. Databases and collections
+4. Queries and pagination
+5. Storage
+
+
+## Prerequisites {% #prerequisites %}
+
+1. Basic knowledge of JavaScript and Vue.
+2. Have [Node.js](#) and [NPM](#) installed on your computer
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/vue/step-2/+page.markdoc b/src/routes/docs/tutorials/vue/step-2/+page.markdoc
new file mode 100644
index 0000000000..a9e3e902fc
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-2/+page.markdoc
@@ -0,0 +1,28 @@
+---
+layout: tutorial
+title: Create app
+description: This is the description used for SEO.
+step: 2
+---
+
+## Create Vue project {% #create-vue-project %}
+
+Create a Vue app with the `npm create` command.
+
+```sh
+npm create vite@latest --template vue ideas-tracker && cd ideas-tracker
+```
+
+## Add dependencies {% #add-dependencies %}
+
+Install the JavaScript Appwrite SDK.
+
+```sh
+npm install appwrite
+```
+
+You can start the development server to watch your app update in the browser as you make changes.
+
+```sh
+npm run dev -- --open --port 3000
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/vue/step-3/+page.markdoc b/src/routes/docs/tutorials/vue/step-3/+page.markdoc
new file mode 100644
index 0000000000..14ea98d6dc
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-3/+page.markdoc
@@ -0,0 +1,42 @@
+---
+layout: tutorial
+title: Set up Appwrite
+description: This is the description used for SEO.
+step: 3
+---
+
+## Create project {% #create-project %}
+
+Head to the [Appwrite Console](https://cloud.appwrite.io/console).
+
+
+
+If this is your first time using Appwrite, create an account and create your first project.
+
+Then, under **Add a platform**, add a **Web app**. The **Hostname** should be localhost.
+
+
+
+You can skip optional steps.
+
+## Initialize Appwrite SDK {% #init-sdk %}
+
+To use Appwrite in our Svelte app, we'll need to find our project ID. Find your project's ID in the **Settings** page.
+
+
+
+Create a new file `src/appwrite.js` to hold our Appwrite related code.
+Only one instance of the `Client()` class should be created per app.
+Add the following code to it, replacing `` with your project ID.
+
+```js
+import { Client } from "appwrite";
+
+const client = new Client();
+client
+ .setEndpoint("https://cloud.appwrite.io/v1")
+ .setProject(""); // Replace with your project IDxw
+
+export const account = new Account(client);
+export const database = new Database(client);
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/vue/step-4/+page.markdoc b/src/routes/docs/tutorials/vue/step-4/+page.markdoc
new file mode 100644
index 0000000000..3011dac624
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-4/+page.markdoc
@@ -0,0 +1,145 @@
+---
+layout: tutorial
+title: Add authentication
+description: This is the description used for SEO.
+step: 4
+---
+
+## User store
+
+In Vue, you can use the [reactive](https://vuejs.org/guide/essentials/reactivity-fundamentals.html#reactive) API to share data between components.
+We'll create a store to share the user's data between components.
+
+Create a new file `src/lib/stores/user.js` and add the following code to it.
+
+```js
+import { ID } from "appwrite";
+import { account } from "../appwrite";
+import { reactive } from "vue";
+
+export const user = reactive({
+ current: null,
+ async init() {
+ try {
+ this.current = await account.get();
+ } catch (e) {
+ this.current = null;
+ }
+ },
+ async register(email, password) {
+ await account.create(ID.unique(), email, password);
+ await this.login(email, password);
+ },
+ async login(email, password) {
+ await account.createEmailSession(email, password);
+ window.location.href = "/"; // Redirect to home page
+ },
+ async logout() {
+ await account.deleteSession("current");
+ this.current = null;
+ },
+});
+
+```
+
+Now, we can import the `user` store in any component and use it to login, logout, or register a user. However, we'll need to call the `init` method to initialize the user's data.
+
+## Basic routing
+
+First, import the `user` store in `src/App.vue` and call the `init` method when the component is mounted.
+
+Update `src/App.vue` to the following code.
+
+```vue
+
+
+
+
+ Home page
+
+
+```
+
+You can use the [Vue Router](https://router.vuejs.org/) to handle routing in your app. However, we'll keep it simple for now.
+Optionally render a `Login` component if the path is `/login`, otherwise render the `Home` component.
+
+Update `src/App.jsx` to the following code.
+
+```vue
+
+
+
+
+
+
+
+
+
+
+```
+
+
+
+## Home page
+
+Create a new file `src/pages/Home.vue` and add the following stub code to it.
+
+```vue
+
+
+
Home page
+
+```
+
+## Login page
+
+Finally, we are able to create the login page. Users will be able to login or register from this page, so we'll need to add two buttons.
+
+Create a new file `src/pages/Login.vue` and add the following code to it.
+
+```vue
+
+
+
+
+
Login or register
+
+
+
+```
+
diff --git a/src/routes/docs/tutorials/vue/step-5/+page.markdoc b/src/routes/docs/tutorials/vue/step-5/+page.markdoc
new file mode 100644
index 0000000000..be96d704b4
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-5/+page.markdoc
@@ -0,0 +1,48 @@
+---
+layout: tutorial
+title: Add navigation
+description: This is the description used for SEO.
+step: 5
+difficulty: easy
+readtime: 10
+---
+
+In our app we want to have a navigation bar that is always visible. Use the `user` store to show either:
+- a logout button if the user is logged in.
+- a login button if the user is not logged in.
+
+Update the App componenent in `src/App.vue`:
+
+```vue
+
+
+
+
+
+
+
+
+
+
+
+```
diff --git a/src/routes/docs/tutorials/vue/step-6/+page.markdoc b/src/routes/docs/tutorials/vue/step-6/+page.markdoc
new file mode 100644
index 0000000000..62f693536b
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-6/+page.markdoc
@@ -0,0 +1,61 @@
+---
+layout: tutorial
+title: Add database
+description: This is the description used for SEO.
+step: 6
+difficulty: easy
+readtime: 10
+---
+## Create collection
+In Appwrite, data is stored as a collection of documents. Create a collection in the [Appwrite Console](https://cloud.appwrite.io/) to store our ideas.
+
+
+
+Create a new collection with the following attributes:
+| Field | Type | Required |
+|-------------|--------|----------|
+| userId | String | Yes |
+| title | String | Yes |
+| description | String | No |
+
+## Ideas context
+
+Now that you have a collection to hold ideas, we can read and write to it from our app. Like we did with the user data, we will create a store hold our ideas.
+Create a new file `src/lib/stores/ideas.js` and add the following code to it.
+
+```js
+import { ID, Query } from "appwrite";
+import { databases } from "../appwrite";
+import { reactive } from "vue";
+
+export const IDEAS_DATABASE_ID = ""; // Replace with your database ID
+export const IDEAS_COLLECTION_ID = ""; // Replace with your collection ID
+
+export const ideas = reactive({
+ current: [],
+ async init() {
+ const response = await databases.listDocuments(
+ IDEAS_DATABASE_ID,
+ IDEAS_COLLECTION_ID,
+ [Query.orderDesc("$createdAt"), Query.limit(10)]
+ );
+ this.current = response.documents;
+ },
+ async add(idea) {
+ const response = await databases.createDocument(
+ IDEAS_DATABASE_ID,
+ IDEAS_COLLECTION_ID,
+ ID.unique(),
+ idea
+ );
+ this.current = [response, ...this.current].slice(0, 10);
+ },
+ async remove(id) {
+ await databases.deleteDocument(IDEAS_DATABASE_ID, IDEAS_COLLECTION_ID, id);
+ this.current = this.current.filter((idea) => idea.$id !== id);
+ await this.init(); // Refetch ideas to ensure we have 10 items
+ },
+});
+```
+
+Note the init function, which uses `Query` to fetch the last 10 ideas from the database. We will call this function when the app starts to ensure we have some data to display.
diff --git a/src/routes/docs/tutorials/vue/step-7/+page.markdoc b/src/routes/docs/tutorials/vue/step-7/+page.markdoc
new file mode 100644
index 0000000000..977d8c1e4a
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-7/+page.markdoc
@@ -0,0 +1,74 @@
+---
+layout: tutorial
+title: Create ideas page
+description: This is the description used for SEO.
+step: 7
+difficulty: easy
+readtime: 10
+---
+
+Using the `ideas` store we can now display the ideas on the page. We will also add a form to submit new ideas.
+
+Overwrite the contents of `src/pages/Home.vue` with the following:
+
+```vue
+
+
+
+
+
Submit Idea
+
+
+
+
Please login to submit an idea.
+
+
+
Latest Ideas
+
+
+ {{ idea.title }}
+
{{ idea.description }}
+
+
+
+
+
+```
\ No newline at end of file
diff --git a/src/routes/docs/tutorials/vue/step-8/+page.markdoc b/src/routes/docs/tutorials/vue/step-8/+page.markdoc
new file mode 100644
index 0000000000..9c5af3c44c
--- /dev/null
+++ b/src/routes/docs/tutorials/vue/step-8/+page.markdoc
@@ -0,0 +1,14 @@
+---
+layout: tutorial
+title: Next steps
+description: This is the description used for SEO.
+step: 8
+difficulty: easy
+readtime: 10
+---
+
+## Test your project {% #test-project %}
+Run your project with `npm run dev -- --open --port 3000` and open [http://localhost:3000](http://localhost:3000) in your browser.
+
+## Add style {% #add-style %}
+If you want to see a version of this project, complete with CSS styles, clone [this GitHub repository]().
\ No newline at end of file
diff --git a/src/routes/kitchensink/+page.svelte b/src/routes/kitchensink/+page.svelte
index 380c281090..8074011045 100644
--- a/src/routes/kitchensink/+page.svelte
+++ b/src/routes/kitchensink/+page.svelte
@@ -73,27 +73,6 @@