3 الالتزامات
main ... main

المؤلف SHA1 الرسالة التاريخ
39949bceaf Update src/App.tsx 2025-10-02 08:48:32 +00:00
80e4f88192 Update Dockerfile 2025-10-02 07:00:58 +00:00
96e9ddd94a Add Dockerfile 2025-10-02 06:51:40 +00:00
2 ملفات معدلة مع 679 إضافات و0 حذوفات

25
Dockerfile Normal file
عرض الملف

@@ -0,0 +1,25 @@
FROM node:20-alpine AS build
WORKDIR /app
# انسخ package.json و package-lock.json
COPY package*.json ./
# نزّل الـ dependencies
RUN npm install
# انسخ باقي الملفات
COPY . .
# نفّذ build باستخدام Vite
RUN npm run build
# المرحلة الثانية: Nginx
FROM nginx:alpine
# انسخ ملفات Vite build (موجودة بـ dist)
COPY --from=build /app/dist /usr/share/nginx/html
# افتح بورت 80
EXPOSE 80
# شغّل Nginx
CMD ["nginx", "-g", "daemon off;"]

عرض الملف

@@ -195,6 +195,660 @@ const mockData: APITestData = {
}
},
"status": "failed"
},
{
"id": 4,
"title": "Valid userId without includePosts",
"input": {
"urlParams": {
"userId": 456
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token"
},
"body": {}
},
"expectedResponse": {
"statusCode": 200,
"body": {
"id": 456,
"name": "Jane Smith"
}
},
"actualResponse": {
"statusCode": 200,
"body": {
"id": 456,
"name": "Jane Smith"
}
},
"status": "passed"
},
{
"id": 5,
"title": "Invalid token format",
"input": {
"urlParams": {
"userId": 123
},
"query": {
"includePosts": false
},
"headers": {
"Authorization": "InvalidToken"
},
"body": {}
},
"expectedResponse": {
"statusCode": 401,
"body": {
"error": "Invalid token format"
}
},
"actualResponse": {
"statusCode": 401,
"body": {
"error": "Invalid token format"
}
},
"status": "passed"
}
]
},
{
"title": "Create New Post",
"method": "POST",
"endpoint": "/posts",
"description": "Create a new blog post",
"urlParams": [],
"query": [],
"headers": [
{
"name": "Authorization",
"type": "string",
"example": "Bearer <token>",
"required": true
},
{
"name": "Content-Type",
"type": "string",
"example": "application/json",
"required": true
}
],
"body": {
"required": true,
"fields": [
{
"name": "title",
"type": "string",
"example": "My First Post",
"required": true,
"description": "Title of the post"
},
{
"name": "content",
"type": "string",
"example": "This is the post content",
"required": true,
"description": "Main content of the post"
},
{
"name": "userId",
"type": "integer",
"example": 123,
"required": true,
"description": "ID of the user creating the post"
},
{
"name": "tags",
"type": "array",
"example": ["tech", "programming"],
"required": false,
"description": "Post tags"
}
]
},
"testCases": [
{
"id": 1,
"title": "Create post with all fields",
"input": {
"urlParams": {},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"title": "My First Post",
"content": "This is the post content",
"userId": 123,
"tags": ["tech", "programming"]
}
},
"expectedResponse": {
"statusCode": 201,
"body": {
"id": 1,
"title": "My First Post",
"content": "This is the post content",
"userId": 123,
"tags": ["tech", "programming"],
"createdAt": "2025-10-02T10:00:00Z"
}
},
"actualResponse": {
"statusCode": 201,
"body": {
"id": 1,
"title": "My First Post",
"content": "This is the post content",
"userId": 123,
"tags": ["tech", "programming"],
"createdAt": "2025-10-02T10:00:00Z"
}
},
"status": "passed"
},
{
"id": 2,
"title": "Missing required field - title",
"input": {
"urlParams": {},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"content": "This is the post content",
"userId": 123
}
},
"expectedResponse": {
"statusCode": 400,
"body": {
"error": "Missing required field: title"
}
},
"actualResponse": {
"statusCode": 400,
"body": {
"error": "Missing required field: title"
}
},
"status": "passed"
},
{
"id": 3,
"title": "Invalid userId",
"input": {
"urlParams": {},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"title": "New Post",
"content": "Content here",
"userId": 9999
}
},
"expectedResponse": {
"statusCode": 404,
"body": {
"error": "User not found"
}
},
"actualResponse": {
"statusCode": 400,
"body": {
"error": "Invalid userId"
}
},
"status": "failed"
},
{
"id": 4,
"title": "Empty content",
"input": {
"urlParams": {},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"title": "Post with no content",
"content": "",
"userId": 123
}
},
"expectedResponse": {
"statusCode": 400,
"body": {
"error": "Content cannot be empty"
}
},
"actualResponse": {
"statusCode": 400,
"body": {
"error": "Content cannot be empty"
}
},
"status": "passed"
},
{
"id": 5,
"title": "Unauthorized request",
"input": {
"urlParams": {},
"query": {},
"headers": {
"Content-Type": "application/json"
},
"body": {
"title": "Unauthorized Post",
"content": "This should not be created",
"userId": 123
}
},
"expectedResponse": {
"statusCode": 401,
"body": {
"error": "Unauthorized"
}
},
"actualResponse": {
"statusCode": 401,
"body": {
"error": "Unauthorized"
}
},
"status": "passed"
}
]
},
{
"title": "Update User Profile",
"method": "PUT",
"endpoint": "/users/{userId}",
"description": "Update user profile information",
"urlParams": [
{
"name": "userId",
"type": "integer",
"example": 123,
"required": true,
"description": "ID of the user to update"
}
],
"query": [],
"headers": [
{
"name": "Authorization",
"type": "string",
"example": "Bearer <token>",
"required": true
},
{
"name": "Content-Type",
"type": "string",
"example": "application/json",
"required": true
}
],
"body": {
"required": true,
"fields": [
{
"name": "name",
"type": "string",
"example": "John Doe",
"required": false,
"description": "User's full name"
},
{
"name": "email",
"type": "string",
"example": "john@example.com",
"required": false,
"description": "User's email address"
},
{
"name": "phone",
"type": "string",
"example": "+1234567890",
"required": false,
"description": "User's phone number"
}
]
},
"testCases": [
{
"id": 1,
"title": "Update user name",
"input": {
"urlParams": {
"userId": 123
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"name": "John Smith"
}
},
"expectedResponse": {
"statusCode": 200,
"body": {
"id": 123,
"name": "John Smith",
"email": "john@example.com",
"phone": "+1234567890"
}
},
"actualResponse": {
"statusCode": 200,
"body": {
"id": 123,
"name": "John Smith",
"email": "john@example.com",
"phone": "+1234567890"
}
},
"status": "passed"
},
{
"id": 2,
"title": "Update multiple fields",
"input": {
"urlParams": {
"userId": 123
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"name": "Jane Doe",
"email": "jane@example.com"
}
},
"expectedResponse": {
"statusCode": 200,
"body": {
"id": 123,
"name": "Jane Doe",
"email": "jane@example.com",
"phone": "+1234567890"
}
},
"actualResponse": {
"statusCode": 200,
"body": {
"id": 123,
"name": "Jane Doe",
"email": "jane@example.com",
"phone": "+1234567890"
}
},
"status": "passed"
},
{
"id": 3,
"title": "Invalid email format",
"input": {
"urlParams": {
"userId": 123
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"email": "invalid-email"
}
},
"expectedResponse": {
"statusCode": 400,
"body": {
"error": "Invalid email format"
}
},
"actualResponse": {
"statusCode": 400,
"body": {
"error": "Invalid email format"
}
},
"status": "passed"
},
{
"id": 4,
"title": "Update non-existent user",
"input": {
"urlParams": {
"userId": 9999
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token",
"Content-Type": "application/json"
},
"body": {
"name": "Ghost User"
}
},
"expectedResponse": {
"statusCode": 404,
"body": {
"error": "User not found"
}
},
"actualResponse": {
"statusCode": 404,
"body": {
"error": "User not found"
}
},
"status": "passed"
},
{
"id": 5,
"title": "Forbidden - update another user",
"input": {
"urlParams": {
"userId": 456
},
"query": {},
"headers": {
"Authorization": "Bearer user_123_token",
"Content-Type": "application/json"
},
"body": {
"name": "Hacker Name"
}
},
"expectedResponse": {
"statusCode": 403,
"body": {
"error": "Forbidden: Cannot update another user's profile"
}
},
"actualResponse": {
"statusCode": 401,
"body": {
"error": "Unauthorized"
}
},
"status": "failed"
}
]
},
{
"title": "Delete Post",
"method": "DELETE",
"endpoint": "/posts/{postId}",
"description": "Delete a blog post by ID",
"urlParams": [
{
"name": "postId",
"type": "integer",
"example": 42,
"required": true,
"description": "ID of the post to delete"
}
],
"query": [],
"headers": [
{
"name": "Authorization",
"type": "string",
"example": "Bearer <token>",
"required": true
}
],
"body": {
"required": false,
"fields": []
},
"testCases": [
{
"id": 1,
"title": "Successfully delete post",
"input": {
"urlParams": {
"postId": 42
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token"
},
"body": {}
},
"expectedResponse": {
"statusCode": 204,
"body": {}
},
"actualResponse": {
"statusCode": 204,
"body": {}
},
"status": "passed"
},
{
"id": 2,
"title": "Delete non-existent post",
"input": {
"urlParams": {
"postId": 9999
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token"
},
"body": {}
},
"expectedResponse": {
"statusCode": 404,
"body": {
"error": "Post not found"
}
},
"actualResponse": {
"statusCode": 404,
"body": {
"error": "Post not found"
}
},
"status": "passed"
},
{
"id": 3,
"title": "Delete without authorization",
"input": {
"urlParams": {
"postId": 42
},
"query": {},
"headers": {},
"body": {}
},
"expectedResponse": {
"statusCode": 401,
"body": {
"error": "Unauthorized"
}
},
"actualResponse": {
"statusCode": 401,
"body": {
"error": "Unauthorized"
}
},
"status": "passed"
},
{
"id": 4,
"title": "Delete post owned by another user",
"input": {
"urlParams": {
"postId": 42
},
"query": {},
"headers": {
"Authorization": "Bearer wrong_user_token"
},
"body": {}
},
"expectedResponse": {
"statusCode": 403,
"body": {
"error": "Forbidden: Cannot delete another user's post"
}
},
"actualResponse": {
"statusCode": 403,
"body": {
"error": "Forbidden: Cannot delete another user's post"
}
},
"status": "passed"
},
{
"id": 5,
"title": "Invalid postId format",
"input": {
"urlParams": {
"postId": "invalid"
},
"query": {},
"headers": {
"Authorization": "Bearer valid_token"
},
"body": {}
},
"expectedResponse": {
"statusCode": 400,
"body": {
"error": "Invalid postId format"
}
},
"actualResponse": {
"statusCode": 500,
"body": {
"error": "Internal server error"
}
},
"status": "failed"
}
]
}