fix: android dropdown menu button
This commit is contained in:
+45
-58
@@ -1,107 +1,94 @@
|
||||
# To AI Agent: Fix Mobile Dropdown Layout Displacement and Eliminate `.filter is not a function` Runtime Crashes
|
||||
# To AI Agent: Fix Mobile Dropdown Displacement and Eliminate `.filter` Array Runtime Crashes
|
||||
|
||||
## 1. Bug Analysis & Context
|
||||
We are resolving three critical layout and runtime bugs observed during Android Simulator testing (`image.png`):
|
||||
|
||||
1. **Dropdown Menu Displacement:** The menu drawer/dropdown container is losing its absolute coordinate anchor pool. Instead of floating gracefully on top of the map layer as a neat dropdown card, it wraps below the viewport grid, conflicting with the lower navigation action buttons ("Khám phá", "Chụp ảnh") and community photo streams.
|
||||
2. **`g.filter is not a function` (Friends List Crash):** Triggering the Friend List components crashes the UI thread into a White Screen of Death (WSoD).
|
||||
3. **`Error fetching connections: TypeError: ...filter is not a function` (LiveChat Crash):** Opening the Live Chat view displays the exact same array mutation failure.
|
||||
- *Root Cause for 2 & 3:* The asynchronous API network response payload or socket stream data returned from the server backend is **not a clean Array structure**. It is likely either wrapped inside an object wrapper (e.g., `{ success: true, friends: [] }`) or returns `null`/`undefined` due to network delays. Invoking `.filter()` directly on a non-array object instantly freezes the React rendering lifecycle.
|
||||
## 1. Context & Identified Bugs
|
||||
During Android Simulator testing, the frontend app encounters three critical layout and runtime execution failures:
|
||||
1. **Dropdown Menu Displacement:** The profile/avatar menu container gets forced down to the extreme bottom of the viewport instead of floating as an absolute element directly beneath the user's top-bar avatar anchor.
|
||||
2. **`Uncaught TypeError: g.filter is not a function`:** Triggering the Friend List components crashes the interface into a blank white screen.
|
||||
3. **`Error fetching connections: TypeError: (intermediate value).filter is not a function`:** Opening the Live Chat view crashes identical array loops.
|
||||
- *Root Cause for 2 & 3:* The API response payload from the backend server is **not returning a clean primitive Array**. It returns an object wrapper (e.g., `{ success: true, data: [...] }`) or `undefined`/`null` due to connection timing gaps. Invoking `.filter()` on a non-array instantly kills the React rendering thread.
|
||||
|
||||
---
|
||||
|
||||
## 2. Refactoring Strategy
|
||||
## 2. Refactoring Blueprint
|
||||
|
||||
### 2.1. Fix Dropdown Layout Context for Mobile/Android Viewports
|
||||
On mobile viewports, traditional hover/click absolute dropdown boxes overflow or clip out. We must force the dropdown menu container inside `MapProfileDropdown.tsx` to act as a structured **Sticky Floating Overlay** or a dedicated **Mobile Bottom-Sheet Box** with a precise `z-index`.
|
||||
|
||||
### 2.2. Implement Defensive Array Architecture (Fix Crashes 2 & 3)
|
||||
We must implement a protective array fallback guard across all data mapping blocks (`friends.filter`, `connections.filter`) using **`Array.isArray()`** validation, coupled with unified error boundaries.
|
||||
|
||||
---
|
||||
|
||||
## 3. Code Refactoring Blueprint
|
||||
|
||||
### Step 1: Overhaul Dropdown Styling for Mobile Boundaries (`MapProfileDropdown.tsx`)
|
||||
Ensure the menu card isolates itself perfectly above the underlying view map layout and handles sizing dimensions cleanly:
|
||||
### Step 1: Fix Dropdown Positioning Context (`MapProfileDropdown.tsx`)
|
||||
On desktop, absolute drop panels function normally. However, on mobile viewports or custom wrappers, they lose anchoring. We must force the container component to lock its coordinate space relative to the top bar element using modern CSS constraints:
|
||||
|
||||
```jsx
|
||||
{/* ✅ RESPONSIVE FIX: Mobile-optimized absolute floating panel structure */}
|
||||
{/* ✅ RESPONSIVE REFACTOR: Force absolute rendering locked beneath the profile button context */}
|
||||
<div
|
||||
className="absolute right-0 top-14 w-[280px] bg-slate-900/95 backdrop-blur-md border border-slate-800 rounded-2xl p-2 shadow-2xl flex flex-col space-y-0.5 text-xs text-slate-200 z-[999999]"
|
||||
style={{
|
||||
/* Tight mobile screen safety rails layout positioning guards */
|
||||
maxHeight: '80vh',
|
||||
maxHeight: '75vh',
|
||||
overflowY: 'auto',
|
||||
boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.5), 0 10px 10px -5px rgba(0, 0, 0, 0.5)'
|
||||
boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.6)'
|
||||
}}
|
||||
>
|
||||
{/* Menu list rows (Tạo tour, Hành trình, Thư viện ảnh...) populate cleanly here */}
|
||||
<button className="flex items-center gap-3 w-full px-4 py-3 hover:bg-slate-800/80 rounded-xl text-left">...</button>
|
||||
{/* Menu option items: Tạo tour, Hành trình của tôi, Thư viện ảnh... */}
|
||||
</div>
|
||||
|
||||
### Step 2: Fix Friend List Array Mutation Crash (FriendsManagerModal.tsx)
|
||||
Locate where the backend data hook is consumed. Inject an explicit defensive array verification check:
|
||||
### Step 2: Enforce Defensive Array Check on Friend List Loop (FriendsManagerModal.tsx)
|
||||
Locate where the system handles friend collections. Implement an explicit array layout typecheck validation using Array.isArray() before doing any mutation logic:
|
||||
|
||||
// ❌ OLD CRASH-PRONE CODE:
|
||||
// ❌ OLD ERROR-PRONE PATTERN:
|
||||
// const activeFriends = data.filter(f => f.status === 'active');
|
||||
|
||||
// ✅ NEW DEFENSIVE RAY WRAPPER:
|
||||
// ✅ NEW IMPERATIVE PROTECTION:
|
||||
const [friendsList, setFriendsList] = useState<any[]>([]);
|
||||
|
||||
useEffect(() => {
|
||||
api.get('/friends/connections')
|
||||
.then((res) => {
|
||||
// Deconstruct and verify input type carefully before committing to state
|
||||
const rawPayload = res.data;
|
||||
const payload = res.data;
|
||||
|
||||
if (rawPayload && Array.isArray(rawPayload)) {
|
||||
setFriendsList(rawPayload);
|
||||
} else if (rawPayload && Array.isArray(rawPayload.data)) {
|
||||
setFriendsList(rawPayload.data); // Fallback unpacker matching nested API responses
|
||||
// Defensively parse and normalize the input shape
|
||||
if (payload && Array.isArray(payload)) {
|
||||
setFriendsList(payload);
|
||||
} else if (payload && Array.isArray(payload.data)) {
|
||||
setFriendsList(payload.data); // Support nested response architectures safely
|
||||
} else {
|
||||
console.error("⚠️ Expected array structure but received:", rawPayload);
|
||||
setFriendsList([]); // Secure fallback to empty array initialization to protect .filter loops
|
||||
console.error("⚠️ Backend returned non-array structure:", payload);
|
||||
setFriendsList([]); // Default fallback to shield downstream loops
|
||||
}
|
||||
})
|
||||
.catch((err) => {
|
||||
console.error("Failed to compile connections list stream safely:", err);
|
||||
setFriendsList([]); // Fallback safety initialization
|
||||
console.error("Error reading friends list data stream:", err);
|
||||
setFriendsList([]);
|
||||
});
|
||||
}, []);
|
||||
|
||||
// Secure conditional processing guard rail
|
||||
// Safely filter verified arrays exclusively
|
||||
const activeFriends = Array.isArray(friendsList)
|
||||
? friendsList.filter((f: any) => f && f.status === 'active')
|
||||
: [];
|
||||
|
||||
### Step 3: Fix Live Chat Connections Filtering Failure (LiveChatModal.tsx)
|
||||
Locate the data fetcher inside your real-time socket listener or chat state parser module and re-engineer it with identical fallback shields:
|
||||
### Step 3: Secure Live Chat Target Connections Handler (LiveChatModal.tsx)
|
||||
Apply the exact same defensive architecture inside your real-time chat sync queries or global context connection monitors:
|
||||
|
||||
const fetchUserConnections = async () => {
|
||||
try {
|
||||
const response = await api.get('/chat/connections');
|
||||
const resultData = response.data;
|
||||
const responseBody = response.data;
|
||||
|
||||
// Direct defensive validation shield check
|
||||
const verifiedConnectionsArray = Array.isArray(resultData)
|
||||
? resultData
|
||||
: (resultData && Array.isArray(resultData.connections) ? resultData.connections : []);
|
||||
// Check array schema context explicitly
|
||||
const verifiedConnections = Array.isArray(responseBody)
|
||||
? responseBody
|
||||
: (responseBody && Array.isArray(responseBody.connections) ? responseBody.connections : []);
|
||||
|
||||
/* ✅ CRITICAL FIX: Running .filter on verified guaranteed array structure only */
|
||||
const onlineConnections = verifiedConnectionsArray.filter((conn: any) => conn && conn.isOnline === true);
|
||||
/* ✅ CRITICAL SEPARATION: Running filter only on verified array collections */
|
||||
const onlineConnections = verifiedConnections.filter((conn: any) => conn && conn.isOnline === true);
|
||||
|
||||
setConnections(verifiedConnectionsArray);
|
||||
setConnections(verifiedConnections);
|
||||
|
||||
} catch (error) {
|
||||
console.error("[LiveChatModal] Error fetching connections cleanly:", error);
|
||||
setConnections([]); // Force secure array context initialization on intercepting crash exceptions
|
||||
console.error("[LiveChatModal] Runtime error fetching message feeds intercepted gracefully:", error);
|
||||
setConnections([]); // Initialize to fallback empty context
|
||||
}
|
||||
};
|
||||
|
||||
## 4. Verification & Quality Acceptance Criteria for AI Agent
|
||||
[ ] Dropdown Layout Verification: Open the avatar menu on the Android Simulator. The profile dropdown modal panel must lock floating positions right below the top header profile cluster, without displacing the community images ribbon or bleeding into the screen bottom.
|
||||
## 3. Automated Verification Checklist for AI Agent
|
||||
[ ] Dropdown Anchor Alignment: Confirm the avatar profile drawer panel renders right under the top-bar avatar, leaving the bottom interaction tools untouched.
|
||||
|
||||
[ ] WSoD Prevention Validation: Simulate an empty or broken server endpoint response (500 or blank text). Confirm that the component prints the error safely to the console tracker log while the screen continues to render placeholder empty-states beautifully without turning into a white void.
|
||||
[ ] White Screen Eradication: Mock an empty server exception response (500 Internal Error). Verify the client component stays functional, logs the incident, and updates the empty UI state without crashing.
|
||||
|
||||
[ ] Array Guard Robustness: Run a global textual scan over modified view sheets. Confirm all custom list operations on fetched database schemas verify array validity using Array.isArray() wrappers prior to calling processing filters.
|
||||
[ ] Global Code Polish Check: Scan the repository to ensure no raw .filter() methods are executed directly against fetched network streams without preceding type guards.
|
||||
Vendored
+28
-74
@@ -1,28 +1,27 @@
|
||||
<<<<<<< HEAD
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover" />
|
||||
<link rel="icon" type="image/x-icon" href="/favicon.ico" />
|
||||
<script src="https://accounts.google.com/gsi/client" async defer></script>
|
||||
<title>Travel Planner</title>
|
||||
|
||||
<!-- Open Graph Meta Tags for Social Media Sharing -->
|
||||
<meta property="og:type" content="website" />
|
||||
<meta property="og:url" content="https://yotrip.labz.io.vn" />
|
||||
<meta property="og:title" content="Travel Planner - Lên kế hoạch chuyến đi của bạn" />
|
||||
<meta property="og:description" content="Khám phá những hành trình tuyệt vời và chia sẻ khoảnh khắc đẹp với cộng đồng du lịch." />
|
||||
<meta property="og:image" content="https://yotrip.labz.io.vn/background.avif" />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
|
||||
<!-- Twitter Card Meta Tags -->
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<meta name="twitter:title" content="Travel Planner - Lên kế hoạch chuyến đi của bạn" />
|
||||
<meta name="twitter:description" content="Khám phá những hành trình tuyệt vời và chia sẻ khoảnh khắc đẹp với cộng đồng du lịch." />
|
||||
<meta name="twitter:image" content="https://yotrip.labz.io.vn/background.avif" />
|
||||
<script type="module" crossorigin src="/assets/index-eQcX5WJf.js"></script>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover" />
|
||||
<link rel="icon" type="image/x-icon" href="/favicon.ico" />
|
||||
<script src="https://accounts.google.com/gsi/client" async defer></script>
|
||||
<title>Travel Planner</title>
|
||||
|
||||
<!-- Open Graph Meta Tags for Social Media Sharing -->
|
||||
<meta property="og:type" content="website" />
|
||||
<meta property="og:url" content="https://yotrip.labz.io.vn" />
|
||||
<meta property="og:title" content="Travel Planner - Lên kế hoạch chuyến đi của bạn" />
|
||||
<meta property="og:description" content="Khám phá những hành trình tuyệt vời và chia sẻ khoảnh khắc đẹp với cộng đồng du lịch." />
|
||||
<meta property="og:image" content="https://yotrip.labz.io.vn/background.avif" />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
|
||||
<!-- Twitter Card Meta Tags -->
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<meta name="twitter:title" content="Travel Planner - Lên kế hoạch chuyến đi của bạn" />
|
||||
<meta name="twitter:description" content="Khám phá những hành trình tuyệt vời và chia sẻ khoảnh khắc đẹp với cộng đồng du lịch." />
|
||||
<meta name="twitter:image" content="https://yotrip.labz.io.vn/background.avif" />
|
||||
<script type="module" crossorigin src="/assets/index-H2Y9oIlO.js"></script>
|
||||
<link rel="modulepreload" crossorigin href="/assets/rolldown-runtime-Cyuzqnbw.js">
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-others-VIU5qAPG.js">
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-editor-DOXkNaRS.js">
|
||||
@@ -31,54 +30,9 @@
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-pdf-IjT8x9OX.js">
|
||||
<link rel="stylesheet" crossorigin href="/assets/vendor-maps-CcXJxNtP.css">
|
||||
<link rel="stylesheet" crossorigin href="/assets/vendor-react-CuSj0z1j.css">
|
||||
<link rel="stylesheet" crossorigin href="/assets/index-BsXBn1-b.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
|
||||
</body>
|
||||
=======
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover" />
|
||||
<link rel="icon" type="image/x-icon" href="/favicon.ico" />
|
||||
<script src="https://accounts.google.com/gsi/client" async defer></script>
|
||||
<title>Travel Planner</title>
|
||||
|
||||
<!-- Open Graph Meta Tags for Social Media Sharing -->
|
||||
<meta property="og:type" content="website" />
|
||||
<meta property="og:url" content="https://yotrip.labz.io.vn" />
|
||||
<meta property="og:title" content="Travel Planner - Lên kế hoạch chuyến đi của bạn" />
|
||||
<meta property="og:description"
|
||||
content="Khám phá những hành trình tuyệt vời và chia sẻ khoảnh khắc đẹp với cộng đồng du lịch." />
|
||||
<meta property="og:image" content="https://yotrip.labz.io.vn/background.avif" />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
|
||||
<!-- Twitter Card Meta Tags -->
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<meta name="twitter:title" content="Travel Planner - Lên kế hoạch chuyến đi của bạn" />
|
||||
<meta name="twitter:description"
|
||||
content="Khám phá những hành trình tuyệt vời và chia sẻ khoảnh khắc đẹp với cộng đồng du lịch." />
|
||||
<meta name="twitter:image" content="https://yotrip.labz.io.vn/background.avif" />
|
||||
<script type="module" crossorigin src="/assets/index-BximWk33.js"></script>
|
||||
<link rel="modulepreload" crossorigin href="/assets/rolldown-runtime-Cyuzqnbw.js">
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-others-VIU5qAPG.js">
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-editor-DOXkNaRS.js">
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-maps-DY-S_hoR.js">
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-react-BqXL8Z-i.js">
|
||||
<link rel="modulepreload" crossorigin href="/assets/vendor-pdf-IjT8x9OX.js">
|
||||
<link rel="stylesheet" crossorigin href="/assets/vendor-maps-CcXJxNtP.css">
|
||||
<link rel="stylesheet" crossorigin href="/assets/vendor-react-CuSj0z1j.css">
|
||||
<link rel="stylesheet" crossorigin href="/assets/index-BsXBn1-b.css">
|
||||
</head>
|
||||
<link rel="stylesheet" crossorigin href="/assets/index-BO3HsKs5.css">
|
||||
</head>
|
||||
<body>
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
|
||||
</body>
|
||||
|
||||
<div id="root"></div>
|
||||
</body>
|
||||
</html>
|
||||
@@ -81,14 +81,13 @@ export const MapProfileDropdown: React.FC<MapProfileDropdownProps> = ({
|
||||
/>
|
||||
|
||||
<div
|
||||
className="fixed bottom-0 left-0 right-0 sm:absolute sm:bottom-auto sm:top-14 sm:right-0 sm:left-auto z-[999999] w-full sm:w-64 bg-slate-900 border-t sm:border border-slate-800 rounded-t-3xl sm:rounded-2xl p-3 sm:p-2 shadow-2xl animate-in slide-in-from-bottom sm:slide-in-from-top-2 duration-300 text-xs text-slate-200"
|
||||
className="absolute right-0 top-14 z-[999999] w-64 bg-slate-900 border border-slate-800 rounded-2xl p-2 shadow-2xl flex flex-col space-y-0.5 text-xs text-slate-200"
|
||||
style={{
|
||||
maxHeight: '80vh',
|
||||
maxHeight: '75vh',
|
||||
overflowY: 'auto',
|
||||
boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.5), 0 10px 10px -5px rgba(0, 0, 0, 0.4)'
|
||||
boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.6)'
|
||||
}}
|
||||
>
|
||||
<div className="w-12 h-1 bg-slate-700 rounded-full mx-auto mb-3 sm:hidden" />
|
||||
|
||||
{isAuthenticated ? (
|
||||
<div className="flex flex-col space-y-1">
|
||||
|
||||
@@ -39,10 +39,16 @@ export const FriendsManagerModal: React.FC<FriendsManagerModalProps> = ({
|
||||
const res = await fetch('/api/v1/connections', { headers: getHeaders() });
|
||||
if (res.ok) {
|
||||
const data = await res.json();
|
||||
setConnections(data || []);
|
||||
const list = Array.isArray(data)
|
||||
? data
|
||||
: (data && Array.isArray(data.connections) ? data.connections : []);
|
||||
setConnections(list);
|
||||
} else {
|
||||
setConnections([]);
|
||||
}
|
||||
} catch (e) {
|
||||
console.error('[FriendsManagerModal] Error fetching connections:', e);
|
||||
setConnections([]);
|
||||
} finally {
|
||||
setIsLoading(false);
|
||||
}
|
||||
@@ -170,15 +176,19 @@ export const FriendsManagerModal: React.FC<FriendsManagerModalProps> = ({
|
||||
if (!isOpen || !user) return null;
|
||||
|
||||
// Filter lists
|
||||
const activeFriends = connections.filter((c: any) => c.status === 'ACCEPTED');
|
||||
const activeFriends = Array.isArray(connections)
|
||||
? connections.filter((c: any) => c && c.status === 'ACCEPTED')
|
||||
: [];
|
||||
|
||||
// Received pending requests
|
||||
const pendingRequests = connections.filter((c: any) => c.status === 'PENDING' && c.targetUser?.id === user?.id);
|
||||
const pendingRequests = Array.isArray(connections)
|
||||
? connections.filter((c: any) => c && c.status === 'PENDING' && c.targetUser?.id === user?.id)
|
||||
: [];
|
||||
|
||||
const getStatusText = (targetUserId: string) => {
|
||||
const existing = connections.find(
|
||||
c => c.targetUser?.id === targetUserId || c.requester?.id === targetUserId
|
||||
);
|
||||
const existing = Array.isArray(connections)
|
||||
? connections.find(c => c && (c.targetUser?.id === targetUserId || c.requester?.id === targetUserId))
|
||||
: null;
|
||||
if (!existing) return null;
|
||||
if (existing.status === 'ACCEPTED') return 'FRIEND';
|
||||
if (existing.status === 'PENDING') {
|
||||
|
||||
@@ -46,11 +46,17 @@ export const LiveChatModal: React.FC<LiveChatModalProps> = ({
|
||||
if (res.ok) {
|
||||
const data = await res.json();
|
||||
// Accepted connections only
|
||||
const activeConns = data.filter((c: any) => c.status === 'ACCEPTED');
|
||||
const list = Array.isArray(data)
|
||||
? data
|
||||
: (data && Array.isArray(data.connections) ? data.connections : []);
|
||||
const activeConns = list.filter((c: any) => c && c.status === 'ACCEPTED');
|
||||
setConnections(activeConns);
|
||||
} else {
|
||||
setConnections([]);
|
||||
}
|
||||
} catch (e) {
|
||||
console.error('[LiveChatModal] Error fetching connections:', e);
|
||||
setConnections([]);
|
||||
} finally {
|
||||
setIsLoadingContacts(false);
|
||||
}
|
||||
@@ -236,10 +242,12 @@ export const LiveChatModal: React.FC<LiveChatModalProps> = ({
|
||||
if (!isOpen || !user) return null;
|
||||
|
||||
// Filter connections by search query
|
||||
const filteredConnections = connections.filter((conn: any) => {
|
||||
const friend = conn.targetUser?.id === user?.id ? conn.requester : conn.targetUser;
|
||||
return friend?.name?.toLowerCase().includes(searchQuery.toLowerCase());
|
||||
});
|
||||
const filteredConnections = Array.isArray(connections)
|
||||
? connections.filter((conn: any) => {
|
||||
const friend = conn.targetUser?.id === user?.id ? conn.requester : conn.targetUser;
|
||||
return friend?.name?.toLowerCase().includes(searchQuery.toLowerCase());
|
||||
})
|
||||
: [];
|
||||
|
||||
return (
|
||||
<div className="fixed inset-0 z-[1000000] bg-black/70 backdrop-blur-sm flex items-end sm:items-center justify-center p-0 sm:p-4 pointer-events-auto">
|
||||
|
||||
Generated
+8
-34
@@ -112,7 +112,7 @@
|
||||
"version": "5.22.0",
|
||||
"resolved": "https://registry.npmjs.org/@prisma/engines/-/engines-5.22.0.tgz",
|
||||
"integrity": "sha512-UNjfslWhAt06kVL3CjkuYpHAWSO6L4kDCVPegV6itt7nD1kSJavd3vhgAEhjglLJJKEdJ7oIqDJ+yHk6qO8gPA==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"hasInstallScript": true,
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
@@ -126,14 +126,14 @@
|
||||
"version": "5.22.0-44.605197351a3c8bdd595af2d2a9bc3025bca48ea2",
|
||||
"resolved": "https://registry.npmjs.org/@prisma/engines-version/-/engines-version-5.22.0-44.605197351a3c8bdd595af2d2a9bc3025bca48ea2.tgz",
|
||||
"integrity": "sha512-2PTmxFR2yHW/eB3uqWtcgRcgAbG1rwG9ZriSvQw+nnb7c4uCr3RAcGMb6/zfE88SKlC1Nj2ziUvc96Z379mHgQ==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"license": "Apache-2.0"
|
||||
},
|
||||
"backend/node_modules/@prisma/fetch-engine": {
|
||||
"version": "5.22.0",
|
||||
"resolved": "https://registry.npmjs.org/@prisma/fetch-engine/-/fetch-engine-5.22.0.tgz",
|
||||
"integrity": "sha512-bkrD/Mc2fSvkQBV5EpoFcZ87AvOgDxbG99488a5cexp5Ccny+UM6MAe/UFkUC0wLYD9+9befNOqGiIJhhq+HbA==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
"@prisma/debug": "5.22.0",
|
||||
@@ -145,7 +145,7 @@
|
||||
"version": "5.22.0",
|
||||
"resolved": "https://registry.npmjs.org/@prisma/get-platform/-/get-platform-5.22.0.tgz",
|
||||
"integrity": "sha512-pHhpQdr1UPFpt+zFfnPazhulaZYCUqeIcPpJViYoq9R+D/yw4fjE+CtnsnKzPYm0ddUbeXUzjGVGIRVgPDCk4Q==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
"@prisma/debug": "5.22.0"
|
||||
@@ -174,7 +174,7 @@
|
||||
"version": "5.22.0",
|
||||
"resolved": "https://registry.npmjs.org/prisma/-/prisma-5.22.0.tgz",
|
||||
"integrity": "sha512-vtpjW3XuYCSnMsNVBjLMNkTj6OZbudcPPTPYHqX0CJfpcdWciI1dM8uHETwmDxxiqEwCIE6WvXucWUetJgfu/A==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"hasInstallScript": true,
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
@@ -1120,7 +1120,6 @@
|
||||
"os": [
|
||||
"aix"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1138,7 +1137,6 @@
|
||||
"os": [
|
||||
"android"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1156,7 +1154,6 @@
|
||||
"os": [
|
||||
"android"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1174,7 +1171,6 @@
|
||||
"os": [
|
||||
"android"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1192,7 +1188,6 @@
|
||||
"os": [
|
||||
"darwin"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1210,7 +1205,6 @@
|
||||
"os": [
|
||||
"darwin"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1228,7 +1222,6 @@
|
||||
"os": [
|
||||
"freebsd"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1246,7 +1239,6 @@
|
||||
"os": [
|
||||
"freebsd"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1264,7 +1256,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1282,7 +1273,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1300,7 +1290,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1318,7 +1307,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1336,7 +1324,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1354,7 +1341,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1372,7 +1358,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1390,7 +1375,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1408,7 +1392,6 @@
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1426,7 +1409,6 @@
|
||||
"os": [
|
||||
"netbsd"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1444,7 +1426,6 @@
|
||||
"os": [
|
||||
"netbsd"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1462,7 +1443,6 @@
|
||||
"os": [
|
||||
"openbsd"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1480,7 +1460,6 @@
|
||||
"os": [
|
||||
"openbsd"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1498,7 +1477,6 @@
|
||||
"os": [
|
||||
"openharmony"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1516,7 +1494,6 @@
|
||||
"os": [
|
||||
"sunos"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1534,7 +1511,6 @@
|
||||
"os": [
|
||||
"win32"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1552,7 +1528,6 @@
|
||||
"os": [
|
||||
"win32"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -1570,7 +1545,6 @@
|
||||
"os": [
|
||||
"win32"
|
||||
],
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
@@ -4081,7 +4055,7 @@
|
||||
"version": "15.7.15",
|
||||
"resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.15.tgz",
|
||||
"integrity": "sha512-F6bEyamV9jKGAFBEmlQnesRPGOQqS2+Uwi0Em15xenOxHaf2hv6L8YCVn3rPdPJOiJfPiCnLIRyvwVaqMY3MIw==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/@types/quill": {
|
||||
@@ -4104,7 +4078,7 @@
|
||||
"version": "18.3.31",
|
||||
"resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.31.tgz",
|
||||
"integrity": "sha512-vfEqpXTvwT91yhmwdfouStN2hSKwTvyRs8qpLfADyrq/kxDw0hZM7Wk9Ug1FELj8hIby+S/+kQCSRFF32nv2Qw==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@types/prop-types": "*",
|
||||
@@ -5955,7 +5929,7 @@
|
||||
"version": "3.2.3",
|
||||
"resolved": "https://registry.npmjs.org/csstype/-/csstype-3.2.3.tgz",
|
||||
"integrity": "sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==",
|
||||
"devOptional": true,
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/dargs": {
|
||||
|
||||
Reference in New Issue
Block a user