Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Pagination #1419

Merged
merged 27 commits into from
Nov 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
41cbcbc
fixing type on env-sample to .env-template
fadingNA Nov 7, 2024
bf0dd69
add page, row_per_page to api/combine
fadingNA Nov 7, 2024
d68e731
revert format code
fadingNA Nov 7, 2024
101935a
add pagination with default code format
fadingNA Nov 7, 2024
a35be6a
add arrow icons for pagination
fadingNA Nov 7, 2024
5dae074
pagination component
fadingNA Nov 7, 2024
ec3407d
add 2 fiels for make request to api/combine
fadingNA Nov 7, 2024
df2f69e
adjust table of document with mx auto, add pagination to Documents Co…
fadingNA Nov 7, 2024
928303f
fix small bug name of page
fadingNA Nov 7, 2024
2a68cc9
calculate totalPage, totalDoc(futreUse)
fadingNA Nov 8, 2024
7ff86a2
remove default value since provide on getDocs
fadingNA Nov 8, 2024
3d03826
add overload function to gettotalpage, and new type
fadingNA Nov 8, 2024
a2967af
adjust Setting/Document to use pagination data from backend
fadingNA Nov 8, 2024
4429755
add paramter type prevent warning lint
fadingNA Nov 8, 2024
dd9589b
fixing type error
fadingNA Nov 8, 2024
5debb48
Paginated With MongoDB / Create New Endpoint
fadingNA Nov 8, 2024
3482474
Pagination
fadingNA Nov 9, 2024
d59ffaf
fix sorting on /sources
fadingNA Nov 9, 2024
f3a005a
remove params on getDocs
fadingNA Nov 9, 2024
0837295
fix table responsive issue
fadingNA Nov 9, 2024
e00c6f2
add min width for delete button, dropdown dakrtheme
fadingNA Nov 9, 2024
b19e9ca
backend fix passing id to paginated docs
fadingNA Nov 10, 2024
839f0a3
remove log on api, add paginatedDoc on redux
fadingNA Nov 10, 2024
1056c94
fix remove button on navigation sidebar and setting/document
fadingNA Nov 10, 2024
6c585de
add paginated to store, and fix upload docs property
fadingNA Nov 10, 2024
32c67c2
add property sync and etc ... to align with original source
fadingNA Nov 10, 2024
6974db5
fix manage sync
fadingNA Nov 10, 2024
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
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ docker compose -f docker-compose-dev.yaml up -d
> Make sure you have Python 3.10 or 3.11 installed.

1. Export required environment variables or prepare a `.env` file in the project folder:
- Copy [.env_sample](https://github.com/arc53/DocsGPT/blob/main/application/.env_sample) and create `.env`.
- Copy [.env-template](https://github.com/arc53/DocsGPT/blob/main/application/.env-template) and create `.env`.

(check out [`application/core/settings.py`](application/core/settings.py) if you want to see more config options.)

Expand Down
85 changes: 77 additions & 8 deletions application/api/user/routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,12 @@
import os
import shutil
import uuid
import math

from bson.binary import Binary, UuidRepresentation
from bson.dbref import DBRef
from bson.objectid import ObjectId
from flask import Blueprint, jsonify, make_response, request
from flask import Blueprint, jsonify, make_response, request, redirect
from flask_restx import inputs, fields, Namespace, Resource
from werkzeug.utils import secure_filename

Expand Down Expand Up @@ -429,12 +430,70 @@


@user_ns.route("/api/combine")
class RedirectToSources(Resource):
@api.doc(
description="Redirects /api/combine to /api/sources for backward compatibility"
)
def get(self):
return redirect("/api/sources", code=301)

Check warning on line 438 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L438

Added line #L438 was not covered by tests


@user_ns.route("/api/sources/paginated")
class PaginatedSources(Resource):
@api.doc(description="Get document with pagination, sorting and filtering")
def get(self):
user = "local"
sort_field = request.args.get("sort", "date") # Default to 'date'
sort_order = request.args.get("order", "desc") # Default to 'desc'
page = int(request.args.get("page", 1)) # Default to 1
rows_per_page = int(request.args.get("rows", 10)) # Default to 10

Check warning on line 449 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L445-L449

Added lines #L445 - L449 were not covered by tests

# Prepare
query = {"user": user}
total_documents = sources_collection.count_documents(query)
total_pages = max(1, math.ceil(total_documents / rows_per_page))
sort_order = 1 if sort_order == "asc" else -1
skip = (page - 1) * rows_per_page

Check warning on line 456 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L452-L456

Added lines #L452 - L456 were not covered by tests

try:
documents = (

Check warning on line 459 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L458-L459

Added lines #L458 - L459 were not covered by tests
sources_collection.find(query)
.sort(sort_field, sort_order)
.skip(skip)
.limit(rows_per_page)
)

paginated_docs = []
for doc in documents:
doc_data = {

Check warning on line 468 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L466-L468

Added lines #L466 - L468 were not covered by tests
"id": str(doc["_id"]),
"name": doc.get("name", ""),
"date": doc.get("date", ""),
"model": settings.EMBEDDINGS_NAME,
"location": "local",
"tokens": doc.get("tokens", ""),
"retriever": doc.get("retriever", "classic"),
"syncFrequency": doc.get("sync_frequency", ""),
}
paginated_docs.append(doc_data)

Check warning on line 478 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L478

Added line #L478 was not covered by tests

response = {

Check warning on line 480 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L480

Added line #L480 was not covered by tests
"total": total_documents,
"totalPages": total_pages,
"currentPage": page,
"paginated": paginated_docs,
}
return make_response(jsonify(response), 200)

Check warning on line 486 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L486

Added line #L486 was not covered by tests

except Exception as err:
return make_response(jsonify({"success": False, "error": str(err)}), 400)

Check warning on line 489 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L488-L489

Added lines #L488 - L489 were not covered by tests


@user_ns.route("/api/sources")
class CombinedJson(Resource):
@api.doc(description="Provide JSON file with combined available indexes")
def get(self):
user = "local"
sort_field = request.args.get('sort', 'date') # Default to 'date'
sort_order = request.args.get('order', "desc") # Default to 'desc'
data = [
{
"name": "default",
Expand All @@ -447,7 +506,7 @@
]

try:
for index in sources_collection.find({"user": user}).sort(sort_field, 1 if sort_order=="asc" else -1):
for index in sources_collection.find({"user": user}).sort("date", -1):

Check warning on line 509 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L509

Added line #L509 was not covered by tests
data.append(
{
"id": str(index["_id"]),
Expand Down Expand Up @@ -485,6 +544,7 @@
"retriever": "brave_search",
}
)

except Exception as err:
return make_response(jsonify({"success": False, "error": str(err)}), 400)

Expand Down Expand Up @@ -1674,7 +1734,9 @@
tts_model = api.model(
"TextToSpeechModel",
{
"text": fields.String(required=True, description="Text to be synthesized as audio"),
"text": fields.String(
required=True, description="Text to be synthesized as audio"
),
},
)

Expand All @@ -1686,8 +1748,15 @@
try:
tts_instance = GoogleTTS()
audio_base64, detected_language = tts_instance.text_to_speech(text)
return make_response(jsonify({"success": True,'audio_base64': audio_base64,'lang':detected_language}), 200)
return make_response(

Check warning on line 1751 in application/api/user/routes.py

View check run for this annotation

Codecov / codecov/patch

application/api/user/routes.py#L1751

Added line #L1751 was not covered by tests
jsonify(
{
"success": True,
"audio_base64": audio_base64,
"lang": detected_language,
}
),
200,
)
except Exception as err:
return make_response(jsonify({"success": False, "error": str(err)}), 400)


14 changes: 13 additions & 1 deletion frontend/src/Navigation.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -34,10 +34,12 @@ import {
selectSelectedDocs,
selectSelectedDocsStatus,
selectSourceDocs,
selectPaginatedDocuments,
setConversations,
setModalStateDeleteConv,
setSelectedDocs,
setSourceDocs,
setPaginatedDocuments,
} from './preferences/preferenceSlice';
import Spinner from './assets/spinner.svg';
import SpinnerDark from './assets/spinner-dark.svg';
Expand Down Expand Up @@ -72,6 +74,7 @@ export default function Navigation({ navOpen, setNavOpen }: NavigationProps) {
const conversations = useSelector(selectConversations);
const modalStateDeleteConv = useSelector(selectModalStateDeleteConv);
const conversationId = useSelector(selectConversationId);
const paginatedDocuments = useSelector(selectPaginatedDocuments);
const [isDeletingConversation, setIsDeletingConversation] = useState(false);

const { isMobile } = useMediaQuery();
Expand Down Expand Up @@ -143,9 +146,18 @@ export default function Navigation({ navOpen, setNavOpen }: NavigationProps) {
})
.then((updatedDocs) => {
dispatch(setSourceDocs(updatedDocs));
const updatedPaginatedDocs = paginatedDocuments?.filter(
(document) => document.id !== doc.id,
);
dispatch(
setPaginatedDocuments(updatedPaginatedDocs || paginatedDocuments),
);
dispatch(
setSelectedDocs(
updatedDocs?.find((doc) => doc.name.toLowerCase() === 'default'),
Array.isArray(updatedDocs) &&
updatedDocs?.find(
(doc: Doc) => doc.name.toLowerCase() === 'default',
),
),
);
})
Expand Down
3 changes: 2 additions & 1 deletion frontend/src/api/endpoints.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
const endpoints = {
USER: {
DOCS: '/api/combine',
DOCS: '/api/sources',
DOCS_CHECK: '/api/docs_check',
DOCS_PAGINATED: '/api/sources/paginated',
API_KEYS: '/api/get_api_keys',
CREATE_API_KEY: '/api/create_api_key',
DELETE_API_KEY: '/api/delete_api_key',
Expand Down
5 changes: 3 additions & 2 deletions frontend/src/api/services/userService.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,9 @@ import apiClient from '../client';
import endpoints from '../endpoints';

const userService = {
getDocs: (sort = 'date', order = 'desc'): Promise<any> =>
apiClient.get(`${endpoints.USER.DOCS}?sort=${sort}&order=${order}`),
getDocs: (): Promise<any> => apiClient.get(`${endpoints.USER.DOCS}`),
getDocsWithPagination: (query: string): Promise<any> =>
apiClient.get(`${endpoints.USER.DOCS_PAGINATED}?${query}`),
checkDocs: (data: any): Promise<any> =>
apiClient.post(endpoints.USER.DOCS_CHECK, data),
getAPIKeys: (): Promise<any> => apiClient.get(endpoints.USER.API_KEYS),
Expand Down
5 changes: 5 additions & 0 deletions frontend/src/assets/double-arrow-left.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
5 changes: 5 additions & 0 deletions frontend/src/assets/double-arrow-right.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions frontend/src/assets/single-left-arrow.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions frontend/src/assets/single-right-arrow.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
119 changes: 119 additions & 0 deletions frontend/src/components/DocumentPagination.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,119 @@
import React, { useState } from 'react';
import SingleArrowLeft from '../assets/single-left-arrow.svg';
import SingleArrowRight from '../assets/single-right-arrow.svg';
import DoubleArrowLeft from '../assets/double-arrow-left.svg';
import DoubleArrowRight from '../assets/double-arrow-right.svg';

interface PaginationProps {
currentPage: number;
totalPages: number;
rowsPerPage: number;
onPageChange: (page: number) => void;
onRowsPerPageChange: (rows: number) => void;
}

const Pagination: React.FC<PaginationProps> = ({
currentPage,
totalPages,
rowsPerPage,
onPageChange,
onRowsPerPageChange,
}) => {
const [rowsPerPageOptions] = useState([5, 10, 15, 20]);

const handlePreviousPage = () => {
if (currentPage > 1) {
onPageChange(currentPage - 1);
}
};

const handleNextPage = () => {
if (currentPage < totalPages) {
onPageChange(currentPage + 1);
}
};

const handleFirstPage = () => {
onPageChange(1);
};

const handleLastPage = () => {
onPageChange(totalPages);
};

return (
<div className="flex items-center text-xs justify-end gap-4 mt-2 p-2 border-gray-200">
<div className="flex items-center gap-2 ">
<span className="text-gray-900 dark:text-gray-50">Rows per page:</span>
<select
value={rowsPerPage}
onChange={(e) => onRowsPerPageChange(Number(e.target.value))}
className="border border-gray-300 rounded px-2 py-1 dark:bg-dark-charcoal dark:text-gray-50"
>
{rowsPerPageOptions.map((option) => (
<option
className="bg-white dark:bg-dark-charcoal dark:text-gray-50"
key={option}
value={option}
>
{option}
</option>
))}
</select>
</div>

<div className="text-gray-900 dark:text-gray-50">
Page {currentPage} of {totalPages}
</div>

<div className="flex items-center gap-2 text-gray-900 dark:text-gray-50">
<button
onClick={handleFirstPage}
disabled={currentPage === 1}
className="px-2 py-1 border rounded disabled:opacity-50"
>
<img
src={DoubleArrowLeft}
alt="arrow"
className="dark:invert dark:sepia dark:brightness-200"
/>
</button>
<button
onClick={handlePreviousPage}
disabled={currentPage === 1}
className="px-2 py-1 border rounded disabled:opacity-50"
>
<img
src={SingleArrowLeft}
alt="arrow"
className="dark:invert dark:sepia dark:brightness-200"
/>
</button>
<button
onClick={handleNextPage}
disabled={currentPage === totalPages}
className="px-2 py-1 border rounded disabled:opacity-50"
>
<img
src={SingleArrowRight}
alt="arrow"
className="dark:invert dark:sepia dark:brightness-200"
/>
</button>
<button
onClick={handleLastPage}
disabled={currentPage === totalPages}
className="px-2 py-1 border rounded disabled:opacity-50"
>
<img
src={DoubleArrowRight}
alt="arrow"
className="dark:invert dark:sepia dark:brightness-200"
/>
</button>
</div>
</div>
);
};

export default Pagination;
11 changes: 6 additions & 5 deletions frontend/src/hooks/useDefaultDocument.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,11 +17,12 @@ export default function useDefaultDocument() {
getDocs().then((data) => {
dispatch(setSourceDocs(data));
if (!selectedDoc)
data?.forEach((doc: Doc) => {
if (doc.model && doc.name === 'default') {
dispatch(setSelectedDocs(doc));
}
});
Array.isArray(data) &&
data?.forEach((doc: Doc) => {
if (doc.model && doc.name === 'default') {
dispatch(setSelectedDocs(doc));
}
});
});
};

Expand Down
4 changes: 2 additions & 2 deletions frontend/src/index.css
Original file line number Diff line number Diff line change
Expand Up @@ -50,11 +50,11 @@ body.dark {

@layer components {
.table-default {
@apply block w-max table-auto content-center justify-center rounded-xl border border-silver dark:border-silver/40 text-center dark:text-bright-gray;
@apply block w-full mx-auto table-auto content-start justify-center rounded-xl border border-silver dark:border-silver/40 text-center dark:text-bright-gray overflow-auto;
}

.table-default th {
@apply p-4 w-[244px] font-normal text-gray-400; /* Remove border-r */
@apply p-4 w-full font-normal text-gray-400 text-nowrap; /* Remove border-r */
}

.table-default th:last-child {
Expand Down
Loading