Merge branch 'master' of bitbucket.org:LuckyLaszlo/ft_transcendence

This commit is contained in:
cherif
2023-01-17 00:43:19 +01:00
22 changed files with 613 additions and 635 deletions

View File

@@ -1,3 +1,5 @@
import { HttpException, HttpStatus, Injectable, Res } from '@nestjs/common';
import { WsException } from '@nestjs/websockets';
import { WebSocketGateway, SubscribeMessage, WebSocketServer, MessageBody, ConnectedSocket, OnGatewayConnection, OnGatewayDisconnect } from '@nestjs/websockets';
import { UsersService } from 'src/users/users.service';
import { ChatService } from './chat.service';
@@ -22,12 +24,16 @@ implements OnGatewayConnection, OnGatewayDisconnect
@WebSocketServer()
server;
async handleConnection(socket: socketDto) {
async handleConnection(socket: socketDto)
{
printCaller('- socket connected :', socket.id, socket.handshake.query.username);
socket.username = socket.handshake.query.username.toString();
this.sockets.set(socket.username, socket);
if (!socket.username)
return;
this.sockets.set(socket.username, socket);
printCaller("--- socket.username:", socket.username);
let not_emit: string = `${socket.username}_not_emit`;

View File

@@ -1,2 +0,0 @@
WEBSITE_HOST=localhost
WEBSITE_PORT=8080

View File

@@ -18,6 +18,7 @@
{#if ($location !== '/')}
<Header/>
{/if}
<Chat />
<Router routes={primaryRoutes} on:conditionsFailed={conditionsFailed}/>

View File

@@ -1,30 +1,36 @@
<script lang="ts">
import Canvas from "../pieces/Canvas.svelte";
import { push } from "svelte-spa-router";
import { onMount } from 'svelte';
import { push } from "svelte-spa-router";
import { onMount } from 'svelte';
let user;
import { fetchUser } from "../pieces/utils";
let user;
onMount(async () => {
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`)
.then((resp) => resp.json())
if (user && user.statusCode && user.statusCode === 403) {
console.log('on mount no user, returned status code 403 so logging out of userStore')
}
user = await fetchUser();
});
const login = async() => {
window.location.href = `http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth`;
console.log('you are now logged in');
}
const login = async() => {
window.location.href = `http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth`;
console.log('you are now logged in');
}
const logout = async() => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/logout`, {
method: 'POST',
});
user = undefined;
const logout = async() => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/logout`,
{
method: 'POST'
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch logout: ", error);
});
user = null;
};
</script>

View File

@@ -1,44 +1,59 @@
<script lang="ts">
import { onMount } from "svelte";
import { push } from "svelte-spa-router";
import { onMount } from "svelte";
import { push } from "svelte-spa-router";
let qrCodeImg;
let qrCode = "";
let wrongCode = "";
const fetchQrCodeImg = (async () => {
qrCodeImg = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/2fa/generate`,
{
method: "POST",
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.blob();
})
.then((blob) => {
return URL.createObjectURL(blob);
})
.catch((error) => {
console.log("catch fetchQrCodeImg: ", error);
});
let qrCodeImg;
let qrCode = "";
let wrongCode = "";
const fetchQrCodeImg = (async() => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/2fa/generate`,
{
method: 'POST',
})
.then(response => {return response.blob()})
.then(blob => {
const url = URL.createObjectURL(blob);
qrCodeImg = url;
});
})()
})();
const submitCode = async() => {
const response = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/2fa/check`,
{
method : 'POST',
headers : {
"Content-Type": "application/json",
},
body : JSON.stringify({
"twoFaCode" : qrCode,
}),
});
if (response.status === 401) {
qrCode = "";
wrongCode = `Wrong code`;
}
if (response.status === 200) {
push('/profile');
console.log('valid Code for 2FA')
}
};
const submitCode = async () => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/2fa/check`,
{
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
twoFaCode: qrCode,
}),
}
)
.then((response) => {
if (!response.ok) {
if (response.status === 401) {
qrCode = "";
wrongCode = `Wrong code`;
}
throw new Error("HTTP " + response.status);
}
push("/profile");
console.log("valid Code for 2FA");
})
.catch((error) => {
console.log("catch submitCode: ", error);
});
};
</script>

View File

@@ -14,8 +14,8 @@
let user;
let allUsers;
let playerOneAvatar;
let playerTwoAvatar;
let playerOneAvatar = "";
let playerTwoAvatar = "";
//Game's stuff
const options = new pong.InitOptions();

View File

@@ -5,13 +5,13 @@
import MatchListElem from "../../pieces/MatchListElem.svelte";
import type { Match } from "../../pieces/Match";
import { fetchUser, fetchAllUsers, fetchAvatar } from "../../pieces/utils";
import { fetchAvatar } from "../../pieces/utils";
import * as pongSpectator from "./client/pongSpectator";
import { gameState } from "./client/ws";
let playerOneAvatar;
let playerTwoAvatar;
let playerOneAvatar = "";
let playerTwoAvatar = "";
//Game's stuff
const gameAreaId = "game_area";

View File

@@ -1,28 +1,37 @@
<script lang="ts">
import { onMount, onDestroy } from "svelte";
import { fetchUser } from "../../pieces/utils";
let user;
let allUsersRanking = [];
let fetchScoresInterval;
//user's stuff
let currentUser;
let allUsers = [];
let idInterval;
onMount( async() => {
currentUser = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`)
.then( x => x.json() );
allUsers = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/game/ranking`)
.then( x => x.json() );
idInterval = setInterval(fetchScores, 10000);
user = await fetchUser();
allUsersRanking = await fetchScores();
fetchScoresInterval = setInterval(fetchScores, 10000);
})
onDestroy( async() => {
clearInterval(idInterval);
clearInterval(fetchScoresInterval);
})
function fetchScores() {
fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/game/ranking`)
.then( x => x.json() )
.then( x => allUsers = x );
async function fetchScores()
{
return fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/game/ranking`)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.json();
})
.catch((error) => {
console.log("catch fetchScores: ", error);
return [];
});
}
</script>
@@ -41,18 +50,18 @@
</tr>
</thead>
<tbody>
{#each allUsers as user, i}
{#each allUsersRanking as userRanking, i}
<tr>
<th>{i + 1}</th>
{#if user.username === currentUser.username}
<td><b>{user.username} [You]</b></td>
{#if userRanking.username === user.username}
<td><b>{userRanking.username} [You]</b></td>
{:else}
<td>{user.username}</td>
<td>{userRanking.username}</td>
{/if}
<td>{user.stats.winGame}</td>
<td>{user.stats.loseGame}</td>
<td>{user.stats.drawGame}</td>
<td>{user.stats.totalGame}</td>
<td>{userRanking.stats.winGame}</td>
<td>{userRanking.stats.loseGame}</td>
<td>{userRanking.stats.drawGame}</td>
<td>{userRanking.stats.totalGame}</td>
</tr>
{/each}
</tbody>

View File

@@ -60,7 +60,8 @@ function start_after_countdown()
window.addEventListener(
'keydown',
(e) => {
e.preventDefault();
if (e.key === "ArrowUp" || e.key === "ArrowDown")
e.preventDefault();
pong.addKey(e.key);
},
{signal: abortControllerKeydown.signal}
@@ -70,7 +71,8 @@ function start_after_countdown()
window.addEventListener(
'keyup',
(e) => {
e.preventDefault();
if (e.key === "ArrowUp" || e.key === "ArrowDown")
e.preventDefault();
pong.deleteKey(e.key);
},
{signal: abortControllerKeyup.signal}

View File

@@ -1,17 +1,17 @@
<script lang="ts">
import { onMount } from 'svelte';
import { onMount } from 'svelte';
import GenerateUserDisplay from '../../pieces/GenerateUserDisplay.svelte';
import { push } from 'svelte-spa-router';
import { push } from 'svelte-spa-router';
let user;
import Chat from '../../pieces/chat/Chat.svelte';
import { fetchUser } from "../../pieces/utils";
onMount( async() => {
// console.log('mounting profile display')
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`)
.then( (x) => x.json() );
})
let user;
onMount( async() => {
user = await fetchUser();
})
</script>

View File

@@ -1,38 +1,25 @@
<script lang="ts">
/* ProfileDisplayOneUser is the same as DisplayAUser except sources the username from params from router rather than
from a regular var. But yea it's functionally identical, seemed easier to just have a duplicate rather than figuring
out how to get a more complicated things to do 2 jobs.*/
/* ProfileDisplayOneUser is the same as DisplayAUser except sources the username from params from router rather than
from a regular var. But yea it's functionally identical, seemed easier to just have a duplicate rather than figuring
out how to get a more complicated things to do 2 jobs.*/
import { onMount } from 'svelte';
import GenerateUserDisplay from '../../pieces/GenerateUserDisplay.svelte';
import { fetchUser } from "../../pieces/utils";
import { onMount } from 'svelte';
import GenerateUserDisplay from '../../pieces/GenerateUserDisplay.svelte';
export let params;
let oneUser;
export let params;
let user;
onMount( async() => {
oneUser = await fetchUser(params.username);
})
onMount( async() => {
// console.log('Display One User username: '+ params.username)
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user?username=${params.username}`)
.then( (x) => x.json() );
console.log('in display ONE user')
console.log({...user})
})
export const updateUser = async() => {
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user?username=${params.username}`)
.then( (x) => x.json() );
};
$: params.username, updateUser();
</script>
<div class="background-pages">
{#if user !== undefined}
<GenerateUserDisplay user={user}/>
{#if oneUser}
<GenerateUserDisplay user={oneUser}/>
{:else}
<h2>Sorry</h2>
<div>Failed to load user {params.username}</div>
@@ -41,4 +28,3 @@
<!-- This is where i might toss in an Invite to Game button ? -->
</div>

View File

@@ -1,37 +1,33 @@
<script lang="ts">
import Card from '../../pieces/Card.svelte';
import {onMount} from 'svelte';
import { push } from 'svelte-spa-router';
import Button from '../../pieces/Button.svelte';
import { fetchAvatar } from "../../pieces/utils";
import { error } from '../game/client/message';
import Card from '../../pieces/Card.svelte';
import {onMount} from 'svelte';
import { push } from 'svelte-spa-router';
import Button from '../../pieces/Button.svelte';
import { fetchUser, fetchAvatar } from "../../pieces/utils";
let user;
let avatar, newAvatar;
let uploadAvatarSuccess = false;
let user;
let avatar, newAvatar;
let uploadAvatarSuccess = false;
// tbh i might not need this...
let set = { username: '', tfa: false };
let nameTmp; // annoying...
const errors = { username: '', checkbox: '', avatar: ''};
let success = {username: '', avatar: '' };
// tbh i might not need this...
let set = { username: '', tfa: false };
let nameTmp; // annoying...
const errors = { username: '', checkbox: '', avatar: ''};
let success = {username: '', avatar: '' };
onMount( async() => {
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`)
.then( (x) => x.json() );
// do a .catch?
user = await fetchUser();
avatar = await fetchAvatar();
if (user === undefined) {
if (!user) {
console.log('User did not load, something more official should prolly happen')
}
// i don't unerstand why this is necessary but it really doesn't like it otherwise
nameTmp = user.username;
set.tfa = user.isEnabledTwoFactorAuth;
avatar = await fetchAvatar(user.username);
})
const settingsHandler = async() => {
@@ -69,14 +65,60 @@
}
)
.catch((err) => errors.username = err)
const settingsHandler = async() =>
{
// TODO Luke <--> Eric : Explications
// I don't really care which i use at this point...
// if (set.username === nameTmp) {
if ((set.username.trim() === '') && set.tfa === user.isEnabledTwoFactorAuth) {
errors.username = 'Invalid new username';
return;
}
else if ((set.username.trim() === '') && set.tfa !== user.isEnabledTwoFactorAuth) {
set.username = user.username
}
else {
errors.username = '';
}
// .then((result) => console.log(result))
// .then(() => console.log('successful sub of new settings'))
};
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`,
{
method: 'PATCH',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
"username": set.username,
"isEnabledTwoFactorAuth": set.tfa
})
}
)
.then((response) => {
if (!response.ok) {
errors.username = "Something went wrong";
if (response.status === 409) {
errors.username = `${set.username} is already in use, pick a different one.`;
}
throw new Error("HTTP " + response.status);
}
else {
if (response.status === 200) {
success.username = "Your changes have been saved";
}
else if (response.status === 201) {
push("/2fa");
}
}
})
.catch((error) => {
console.log("catch settingsHandler: ", error);
});
}
const uploadAvatar = async() => {
errors.avatar = '';
if (newAvatar === undefined) {
if (!newAvatar) {
errors.avatar = 'You need to pick a file.'
return;
}
@@ -86,19 +128,23 @@
// tmp
console.log(data);
const responseWhenChangeAvatar = fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user/avatar`,
{
method : 'POST',
body : data,
})
const responseFromServer = await responseWhenChangeAvatar;
if (responseFromServer.ok === true) {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user/avatar`,
{
method : 'POST',
body : data,
}
)
.then((response) => {
if (!response.ok) {
errors.avatar = response.statusText;
throw new Error("HTTP " + response.status);
}
uploadAvatarSuccess = true;
success.avatar = 'Your avatar has been updated';
}
else {
errors.avatar = responseFromServer.statusText;
}
})
.catch((error) => {
console.log("catch uploadAvatar: ", error);
});
avatar = await fetchAvatar(user.username);
}
@@ -131,7 +177,7 @@
<Card>
<!-- ok so it can't actually show us the file we upload until we've uploaded it... -->
{#if avatar !== undefined}
{#if avatar}
<img class="avatar" src={avatar} alt="your avatar"/>
{/if}
<form on:submit|preventDefault={uploadAvatar}>
@@ -142,7 +188,7 @@
<input type="file" bind:files={newAvatar}/>
<div class="error">{errors.avatar}</div>
</div>
<Button type={newAvatar === undefined ? "primary" : "secondary"}>Upload Avatar</Button>
<Button type={!newAvatar ? "primary" : "secondary"}>Upload Avatar</Button>
</form>
</Card>
</div>

View File

@@ -1,232 +1,294 @@
<script lang="ts">
import { onMount } from "svelte";
import Button from "../../pieces/Button.svelte";
import DisplayAUser from "../../pieces/DisplayAUser.svelte";
import Tabs from "../../pieces/Tabs.svelte";
import { fetchUser, fetchAllUsers, fetchAvatar } from "../../pieces/utils";
import { onMount } from "svelte";
import Button from "../../pieces/Button.svelte";
import DisplayAUser from "../../pieces/DisplayAUser.svelte";
import Tabs from "../../pieces/Tabs.svelte";
let user;
let allUsers = [];
let myFriendships = [];
let requestsMade, requestsRecieved;
let blockedUsers = [];
let usernameBeingViewed;
let friendshipStatusFull; // date, reveiverUsername, status
let user;
let allUsers;
let myFriendships;
let requestsMade, requestsRecieved;
let blockedUsers;
let usernameBeingViewed;
let friendshipStatusFull; // date, reveiverUsername, status
/**** Layout variables ****/
let tabItems: string[] = [
"All Users",
"My Friends",
"Friend Requests",
"Blocked Users",
];
let activeTabItem: string = "All Users";
/**** Layout variables ****/
let tabItems: string[] = ['All Users', 'My Friends', 'Friend Requests', 'Blocked Users']
let activeTabItem: string = 'All Users';
onMount(async () => {
user = await fetchUser();
fetchAll();
});
onMount( async() => {
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`)
.then( (x) => x.json() );
const fetchAll = async () => {
// no need to await i think it can load in the background
fetchAllUsers_Wrapper();
fetchMyFriendships();
fetchRequestsMade();
fetchRequestsReceived();
fetchBlockedUsers();
};
fetchAll();
});
/***** Fetch basic things *****/
const fetchAllUsers_Wrapper = async () => {
allUsers = await fetchAllUsers();
if (usernameBeingViewed) {
let found = allUsers.find(
(e) => e.username === usernameBeingViewed
);
if (!found) {
usernameBeingViewed = null;
friendshipStatusFull = null;
}
}
};
const fetchAll = async() => {
// no need to await i think it can load in the background
fetchAllUsers();
fetchMyFriendships();
fetchRequestsMade();
fetchRequestsReceived();
fetchBlockedUsers();
}
// it's more like fetch friendships
// then i need to extract the users
const fetchMyFriendships = async () => {
myFriendships = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/myfriends`)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.json();
})
.catch((error) => {
console.log("catch fetchMyFriendships: ", error);
return [];
});
};
/***** Fetch basic things *****/
const fetchAllUsers = async() => {
allUsers = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user/all`)
.then( x => x.json() );
console.log('got all users ')
console.log({...allUsers})
if (usernameBeingViewed !== undefined) {
let found = allUsers.find(e => e.username === usernameBeingViewed);
// console.log("SEARCHING ALL USERS: ")
// console.log({...found})
if (found === undefined) {
// console.log('none found')
usernameBeingViewed = undefined;
friendshipStatusFull = undefined;
}
}
};
const fetchRequestsMade = async () => {
requestsMade = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/pending`)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.json();
})
.catch((error) => {
console.log("catch fetchRequestsMade: ", error);
return [];
});
};
// it's more like fetch friendships
// then i need to extract the users
const fetchMyFriendships = async() => {
myFriendships = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/myfriends`)
.then( x => x.json() );
const fetchRequestsReceived = async () => {
requestsRecieved = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/received`)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.json();
})
.catch((error) => {
console.log("catch fetchRequestsReceived: ", error);
return [];
});
};
console.log('got my friends ')
console.log({...myFriendships})
};
const fetchBlockedUsers = async () => {
blockedUsers = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/blocked`)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.json();
})
.catch((error) => {
console.log("catch fetchBlockedUsers: ", error);
return [];
});
};
/**** END OF MAIN FETCH ****/
const fetchRequestsMade = async() => {
requestsMade = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/pending`)
.then( x => x.json() );
// returns everything but BLOCKED
const fetchFriendshipFull = async (aUsername) => {
friendshipStatusFull = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/myfriends?username=${aUsername}`)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.json();
})
.catch((error) => {
console.log("catch fetchFriendshipFull: ", error);
return [];
});
};
console.log('got requests made ')
console.log({...requestsMade})
};
const sendFriendRequest = async (aUsername) => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations`,
{
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
receiverUsername: aUsername,
status: "R",
}),
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch sendFriendRequest: ", error);
});
const fetchRequestsReceived = async() => {
requestsRecieved = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/received`)
.then( x => x.json() );
await fetchFriendshipFull(aUsername);
await fetchAll();
};
console.log('got requests received ')
console.log({...requestsRecieved})
};
const viewAUser = async (aUsername) => {
usernameBeingViewed = aUsername;
await fetchFriendshipFull(aUsername);
};
const fetchBlockedUsers = async() => {
blockedUsers = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/blocked`)
.then( x => x.json() );
const acceptFriendRequest = async (relationshipId) => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}/accept`,
{
method: "PATCH",
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch acceptFriendRequest: ", error);
});
console.log('got blocked users, is it empty?')
console.log({...blockedUsers})
console.log(Object.keys(blockedUsers))
};
/**** END OF MAIN FETCH ****/
await fetchFriendshipFull(usernameBeingViewed);
await fetchAll();
activeTabItem = activeTabItem;
};
// returns everything but BLOCKED
const fetchFriendshipFull = async(aUsername) => {
console.log('fetch friendship from a username')
console.log(aUsername)
const declineFriendRequest = async (relationshipId) => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}/decline`,
{
method: "PATCH",
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch declineFriendRequest: ", error);
});
friendshipStatusFull = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/myfriends?username=${aUsername}`)
.then( x => x.json());
await fetchFriendshipFull(usernameBeingViewed);
await fetchAll();
activeTabItem = activeTabItem;
};
console.log({...friendshipStatusFull})
};
const unfriend = async (relationshipId) => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}`,
{
method: "DELETE",
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch unfriend: ", error);
});
const sendFriendRequest = async(aUsername) => {
console.log('sending a friend request')
console.log(aUsername)
await fetchFriendshipFull(usernameBeingViewed);
if (Object.keys(friendshipStatusFull).length === 0) {
friendshipStatusFull = null;
}
const resp = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations`, {
method : "POST",
headers: { 'Content-Type': 'application/json'},
body: JSON.stringify({
"receiverUsername": aUsername,
"status": "R"
})
})
.then( x => x.json())
// .catch( x => console.log({...x}))
await fetchFriendshipFull(aUsername);
await fetchAll();
};
await fetchAll();
activeTabItem = activeTabItem;
};
const viewAUser = async(aUsername) => {
console.log('Profile Friend updating userBeingViewed')
const blockANonFriendUser = async (aUsername) => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations`,
{
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
receiverUsername: aUsername,
status: "B",
}),
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch blockANonFriendUser: ", error);
});
usernameBeingViewed = aUsername;
await fetchFriendshipFull(aUsername);
await fetchAll();
usernameBeingViewed = null;
friendshipStatusFull = null;
console.log('Friendship Status Full')
console.log({...friendshipStatusFull})
};
activeTabItem = activeTabItem;
};
const acceptFriendRequest = async(relationshipId) => {
console.log('accept friend request')
const blockAFriend = async (relationshipId) => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}/block`,
{
method: "PATCH"
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch blockAFriend: ", error);
});
const resp = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}/accept`, {
method: "PATCH"})
.then( x => x.json());
await fetchFriendshipFull(usernameBeingViewed);
await fetchAll();
activeTabItem = activeTabItem;
};
await fetchAll();
usernameBeingViewed = null;
friendshipStatusFull = null;
const declineFriendRequest = async(relationshipId) => {
console.log('decline friend request')
// reloads active tab so you get blocked users for example
activeTabItem = activeTabItem;
};
const resp = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}/decline`, {
method: "PATCH"})
.then( x => x.json());
await fetchFriendshipFull(usernameBeingViewed);
await fetchAll();
activeTabItem = activeTabItem;
};
const unfriend = async(relationshipId) => {
console.log('Unfriend')
const resp = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}`, {
method: "DELETE"})
.then( x => x.json());
await fetchFriendshipFull(usernameBeingViewed);
if (Object.keys(friendshipStatusFull).length === 0)
friendshipStatusFull = undefined;
await fetchAll();
activeTabItem = activeTabItem;
};
const blockANonFriendUser = async(aUsername) => {
console.log('Block a non friend user, their username')
console.log(aUsername)
let sentFriendRequest = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations`, {
method : "POST",
headers: { 'Content-Type': 'application/json'},
body: JSON.stringify({
"receiverUsername": aUsername,
"status": "B"
})
})
.then( x => x.json())
// await fetchBlockedUsers();
// await fetchAllUsers();
await fetchAll();
usernameBeingViewed = undefined;
friendshipStatusFull = undefined;
activeTabItem = activeTabItem;
};
const blockAFriend = async(relationshipId) => {
console.log('blocking a friend, the relationshipID')
console.log(relationshipId)
const resp = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/network/relations/${relationshipId}/block`, {method: "PATCH"})
.then( x => x.json() );
console.log('blocked a user response')
console.log({...resp})
// await fetchBlockedUsers();
// await fetchAllUsers();
await fetchAll();
usernameBeingViewed = undefined;
friendshipStatusFull = undefined;
// reloads active tab so you get blocked users for example
activeTabItem = activeTabItem;
};
const unblockAUser = async(relationshipId) => {
// it's basically the same as unfriending someone cuz unfriending them means the relationship is deleted
await unfriend(relationshipId);
activeTabItem = activeTabItem;
};
const switchTab = async(e) => {
activeTabItem = e.detail;
if (activeTabItem === 'All Users') {
await fetchAllUsers();
} else if (activeTabItem === 'My Friends') {
await fetchMyFriendships();
} else if (activeTabItem === 'Friend Requests') {
await fetchRequestsReceived();
} else if (activeTabItem === 'Blocked Users') {
await fetchBlockedUsers();
console.log('fetching blocked users')
}
if (usernameBeingViewed !== undefined)
fetchFriendshipFull(usernameBeingViewed);
};
const unblockAUser = async (relationshipId) => {
// it's basically the same as unfriending someone cuz unfriending them means the relationship is deleted
await unfriend(relationshipId);
activeTabItem = activeTabItem;
};
const switchTab = async (e) => {
activeTabItem = e.detail;
if (activeTabItem === "All Users") {
await fetchAllUsers_Wrapper();
} else if (activeTabItem === "My Friends") {
await fetchMyFriendships();
} else if (activeTabItem === "Friend Requests") {
await fetchRequestsReceived();
} else if (activeTabItem === "Blocked Users") {
await fetchBlockedUsers();
console.log("fetching blocked users");
}
if (usernameBeingViewed)
fetchFriendshipFull(usernameBeingViewed);
};
</script>
@@ -239,7 +301,7 @@
<div class="sidebar-list">
<Tabs items={tabItems} activeItem={activeTabItem} size="small" on:tabChange={switchTab}/>
{#if activeTabItem === 'All Users' && allUsers !== undefined}
{#if activeTabItem === 'All Users' && allUsers}
<h3>{activeTabItem}</h3>
{#if Object.keys(allUsers).length === 0}
<div class="tip">You are alone on this platform...</div>
@@ -255,7 +317,7 @@
<div class="status sidebar-item">{aUser.status}</div>
<br>
{/each}
{:else if activeTabItem === 'My Friends' && myFriendships !== undefined}
{:else if activeTabItem === 'My Friends' && myFriendships}
<h3>{activeTabItem}</h3>
{#if Object.keys(myFriendships).length === 0}
<div class="tip">You don't have any Friends... Yet!</div>
@@ -268,7 +330,7 @@
{/if}
<br>
{/each}
{:else if activeTabItem === 'Friend Requests' && requestsRecieved !== undefined}
{:else if activeTabItem === 'Friend Requests' && requestsRecieved}
<h3>{activeTabItem}</h3>
{#if Object.keys(requestsRecieved).length === 0}
<div class="tip">You don't have any Friend Requests</div>
@@ -278,7 +340,7 @@
<div class="status sidebar-item">{aUser.status}</div>
<br>
{/each}
{:else if activeTabItem === 'Blocked Users' && blockedUsers !== undefined}
{:else if activeTabItem === 'Blocked Users' && blockedUsers}
<h3>{activeTabItem}</h3>
<!-- seems a little excessive... maybe a lighter way of doing this? doesn't seem like it, i hate it but at least only happens sometimes.default... -->
{#if Object.keys(blockedUsers).length === 0}
@@ -294,7 +356,7 @@
<div class="main-display">
{#if usernameBeingViewed !== undefined}
{#if usernameBeingViewed}
<DisplayAUser aUsername={usernameBeingViewed}/>
<div class="buttons-area">

View File

@@ -1,112 +0,0 @@
<script lang="ts">
import { onMount } from 'svelte';
// rename to PotatoCanvas?
let canvas;
// let img;
let loaded = false;
// i feel like they told me not to do this, new Image(), isn't there another way?
// never mind they do seem to do this shit...
// no idea if this should be in onMount...
const img = new Image();
img.src = 'img/potato_logo.png';
img.onload = () => {
loaded = true;
// not sure if i'll use this...
}
// $: scaleRatio = window.innerWidth / 10;
$: scaleRatio = 30;
$: nPotoatoRows = Math.floor(window.innerHeight / 200);
$: nPotoatoCols = Math.floor(window.innerWidth / 200);
// $: spacing = (canvas.height - (img.height / scaleRatio * (nPotoatoRows - 1) )) / nPotoatoRows;
// apparently i might need to move all my reactive statements outside the onMount... not sure why...
onMount(() => {
// in this on mount we will set the canvas and the img
const ctx = canvas.getContext('2d');
// let frame = requestAnimationFrame(loop);
ctx.width = window.innerWidth;
ctx.height = window.innerHeight;
// console.log(nPotoatoCols);
// img = fetch('img/potato_logo.png');
// Moving the IMG stuff from her out of mount
// let nPotoatoRows = 4;
// $: nPotoatoRows = Math.floor(canvas.height / 200);
let spacing = (canvas.height - (img.height / scaleRatio * (nPotoatoRows - 1) )) / nPotoatoRows;
// $: spacing = (canvas.height - (img.height / scaleRatio * (nPotoatoRows - 1) )) / nPotoatoRows;
// i prolly need a number of potatos X and Y vars
// i could do it so there are more potatos than can fit on the screen, translate them over, and then after some point
// shift them all back to the next position they would be in, so it looks like they keep going to infinity
// let dx = 1.5;
let dx = 1;
// let dy = -0.5;
let dy = -1;
// let startX = spacing;
// let startY = spacing;
// let startX = 0;
// let startY = 0;
let startX = -(spacing * 2.5);
let startY = -(spacing * 2.5);
let x = startX;
let y = startY;
let frame = requestAnimationFrame(loop);
// i don't think i need t...
function loop(t) {
// yea ok a loop in a loop in a loop, horrible idea...
ctx.clearRect(0, 0, canvas.width, canvas.height);
// this has to be at the end, no?
frame = requestAnimationFrame(loop);
// if (x > 900) {
// x = startX;
// y = startY;
// }
// else {
// x += dx;
// y += dy;
// }
for (let i = 0; i < 20; i++) {
for (let j = 0; j < 10; j++) {
// ctx.drawImage(img, x + (i * spacing * 2), y + (j * spacing), img.width / scaleRatio, img.height / scaleRatio);
ctx.drawImage(img, x + (i * spacing), y + (j * spacing), img.width / scaleRatio, img.height / scaleRatio);
}
}
}
return () => {
cancelAnimationFrame(frame);
};
});
</script>
<canvas
bind:this={canvas}
width={window.innerWidth}
height={window.innerHeight}
></canvas>
<style>
canvas {
width: 100%;
height: 100%;
background-color: #666;
}
</style>

View File

@@ -1,30 +1,23 @@
<script lang="ts">
import { onMount } from 'svelte';
import GenerateUserDisplay from './GenerateUserDisplay.svelte';
import { onMount } from 'svelte';
import GenerateUserDisplay from './GenerateUserDisplay.svelte';
import { fetchUser } from "../pieces/utils";
export let aUsername;
let user;
export let aUsername;
let aUser;
onMount( async() => {
// console.log('Display aUser username: '+ aUsername)
onMount( async() => {
aUser = await fetchUser(aUsername);
})
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user?username=${aUsername}`)
.then( (x) => x.json() );
})
export const updateUser = async() => {
user = await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user?username=${aUsername}`)
.then( (x) => x.json() );
};
$: aUsername, updateUser();
$: aUsername, fetchUser(aUsername);
</script>
<div class="background-pages">
{#if user !== undefined}
<GenerateUserDisplay user={user}/>
{#if aUser}
<GenerateUserDisplay user={aUser}/>
{:else}
<h2>Sorry</h2>
<div>Failed to load user {aUsername}</div>

View File

@@ -62,11 +62,11 @@
<!-- is this if excessive? -->
<div class="outer">
{#if user !== undefined}
{#if user}
<main>
<!-- <img class="icon" src="img/default_user_icon.png" alt="default user icon"> -->
<!-- <img class="icon" src="{user.image_url}" alt="default user icon"> -->
<img class="avatar" src="{avatar}" alt="default user icon">
<img class="avatar" src="{avatar}" alt="user avatar">
<div class="error">{errors.avatar}</div>
<div class="username">{user.username}</div>
<div class="rank">Rank:

View File

@@ -1,36 +1,47 @@
<script lang="ts">
import { push } from "svelte-spa-router";
import { location } from 'svelte-spa-router';
import { push } from "svelte-spa-router";
import { location } from 'svelte-spa-router';
// no need, it's just for links
import active from 'svelte-spa-router/active'
// or i could leave them all and not display if they're active?
// no need, it's just for links
import active from 'svelte-spa-router/active'
// or i could leave them all and not display if they're active?
$: current = $location;
$: current = $location;
let handleClickLogout = async () => {
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/logout`, {
method: 'POST',
})
.then( () => push('/') )
console.log('clicked logout header')
};
let handleClickLogout = async () =>
{
await fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/auth/logout`,
{
method: 'POST',
}
)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
})
.catch((error) => {
console.log("catch handleClickLogout: ", error);
});
push('/');
};
</script>
<!-- svelte-ignore a11y-click-events-have-key-events -->
<div class="header">
<img src="/img/logo_potato.png" alt="Potato Pong Logo" on:click={() => (push('/'))}>
<div class="center">
<button class:selected="{current === '/game'}" on:click={() => (push('/game'))}>Play</button>
<button class:selected="{current === '/spectator'}" on:click={() => (push('/spectator'))}>Spectate</button>
<button class:selected="{current === '/ranking'}" on:click={() => (push('/ranking'))}>Ranking</button>
<button class:selected="{current === '/profile'}" on:click={() => (push('/profile'))}>My Profile</button>
<button class:selected="{current === '/profile/users'}" on:click={() => (push('/profile/users'))}>Users</button>
</div>
<button class="logout" on:click={handleClickLogout}>Log Out</button>
<img src="/img/logo_potato.png" alt="Potato Pong Logo" on:click={() => (push('/'))}>
<div class="center">
<button class:selected="{current === '/game'}" on:click={() => (push('/game'))}>Play</button>
<button class:selected="{current === '/spectator'}" on:click={() => (push('/spectator'))}>Spectate</button>
<button class:selected="{current === '/ranking'}" on:click={() => (push('/ranking'))}>Ranking</button>
<button class:selected="{current === '/profile'}" on:click={() => (push('/profile'))}>My Profile</button>
<button class:selected="{current === '/profile/users'}" on:click={() => (push('/profile/users'))}>Users</button>
</div>
<button class="logout" on:click={handleClickLogout}>Log Out</button>
</div>
<style>

View File

@@ -2,6 +2,7 @@
import Layouts from './Chat_layouts.svelte';
import { init_socket } from './Socket_chat';
import { user } from './Store_chat';
import { location } from 'svelte-spa-router';
let style_light =
@@ -40,8 +41,8 @@
bg_light_color: "rgb( 35, 35, 35)",
btn_color: "rgb(220, 220, 220)",
btn_color_hover: "rgb(100, 100, 100)",
btn_color_active: "rgb( 90, 90, 90)",
btn_color_hover: "rgb(160, 160, 160)",
btn_color_active: "rgb(150, 150, 150)",
btn_color_border: "rgb(150, 150, 150)",
btn_light_color: "rgb(235, 235, 235)",
@@ -61,10 +62,6 @@
let style = style_light;
console.log("location:",$location);
if ($location !== '/')
init_socket();
function change_style(loc)
{
console.log("change color, location:", loc);
@@ -78,7 +75,16 @@
style = style_light;
}
$: change_style($location);
init_socket();
$: change_style($location);
$: {
$location;
if (!user)
{
init_socket();
};
};
</script>

View File

@@ -239,11 +239,11 @@ export async function remove_block_user(username: string): Promise<void>
await fetch_chat_request('unblock', FetchMethod.POST, {username: username} );
}
export async function list_block_user(username: string): Promise<string[]>
export async function list_block_user(username: string): Promise<User[]>
{
to_print("in list_block_user");
let response = await fetch_chat_request('listblock', FetchMethod.GET);
let response: FetchResponse = await fetch_chat_request('listblock', FetchMethod.GET);
to_print("response.users:", response.users);
return response.users;

View File

@@ -1,28 +1,28 @@
import io from 'socket.io-client';
import { user, msgs, layout, set_socket, set_user } from './Store_chat';
import { to_print } from './Utils_chat';
import { fetchUser } from '../utils';
const address = `http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}`;
export async function init_socket()
{
to_print("in init_socket");
console.log("here");
const response = await fetch(`${address}/api/v2/user`);
const response_data = await response.json();
to_print("-- response_data:", response_data);
const user = await fetchUser();
if (!user)
return;
set_user(response_data);
set_user(user);
let socket = await io(address,
{
path: '/chat',
query:
{
username: response_data.username,
username: user.username,
},
});
console.log("horo");
set_socket(socket);
socket_states(socket);

View File

@@ -1,7 +1,12 @@
export async function fetchAvatar(username: string)
export async function fetchAvatar(username?: string)
{
return fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user/avatar?username=${username}`)
let url = `http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user/avatar`;
if (username) {
url += `?username=${username}`;
}
return fetch(url)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
@@ -17,18 +22,20 @@ export async function fetchAvatar(username: string)
});
}
export async function fetchUser()
export async function fetchUser(username?: string)
{
return fetch(`http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`)
let url = `http://${process.env.WEBSITE_HOST}:${process.env.WEBSITE_PORT}/api/v2/user`;
if (username) {
url += `?username=${username}`;
}
return fetch(url)
.then((response) => {
if (!response.ok) {
throw new Error("HTTP " + response.status);
}
return response.json();
})
.then((body) => {
return body;
})
.catch((error) => {
console.log("catch fetchUser: ", error);
return null;
@@ -44,9 +51,6 @@ export async function fetchAllUsers()
}
return response.json();
})
.then((body) => {
return body;
})
.catch((error) => {
console.log("catch fetchAllUsers: ", error);
return [];

View File

@@ -7,96 +7,41 @@ import { wrap } from 'svelte-spa-router/wrap'
import Game from '../pages/game/Game.svelte';
import Ranking from '../pages/game/Ranking.svelte';
import GameSpectator from '../pages/game/GameSpectator.svelte';
import { fetchUser } from "../pieces/utils";
async function checkLogin(detail) {
const user = await fetchUser();
if (!user || !user.username) {
return false;
}
else {
return true;
}
}
export const primaryRoutes = {
'/': SplashPage,
'/2fa': TwoFactorAuthentication,
'/game': wrap({
component: Game,
conditions: [
async(detail) => {
const user = await fetch('http://' + process.env.WEBSITE_HOST + ":" + process.env.WEBSITE_PORT + '/api/v2/user')
.then((resp) => resp.json())
console.log('in /profile what is in user')
console.log(user)
if (user && user.username)
return true;
else
return false;
}
]
}),
'/spectator': wrap({
component: GameSpectator,
conditions: [
async(detail) => {
const user = await fetch('http://' + process.env.WEBSITE_HOST + ":" + process.env.WEBSITE_PORT + '/api/v2/user')
.then((resp) => resp.json())
console.log('in /profile what is in user')
console.log(user)
if (user && user.username)
return true;
else
return false;
}
]
}),
'/ranking': wrap({
component: Ranking,
conditions: [
async(detail) => {
const user = await fetch('http://' + process.env.WEBSITE_HOST + ":" + process.env.WEBSITE_PORT + '/api/v2/user')
.then((resp) => resp.json())
console.log('in /profile what is in user')
console.log(user)
if (user && user.username)
return true;
else
return false;
}
]
}),
'/profile': wrap({
component: ProfilePage,
conditions: [
async(detail) => {
const user = await fetch('http://' + process.env.WEBSITE_HOST + ":" + process.env.WEBSITE_PORT + '/api/v2/user')
.then((resp) => resp.json())
console.log('in /profile what is in user')
console.log(user)
if (user && user.username)
return true;
else
return false;
}
]
}),
'/profile/*': wrap({
component: ProfilePage,
conditions: [
async(detail) => {
const user = await fetch('http://' + process.env.WEBSITE_HOST + ":" + process.env.WEBSITE_PORT + '/api/v2/user')
.then((resp) => resp.json())
console.log('in /profile/* what is in user')
console.log(user)
if (user && user.username)
return true;
else
return false;
}
]
}),
'/unauthorized-access': UnauthorizedAccessPage,
'*': NotFound
'/': SplashPage,
'/2fa': TwoFactorAuthentication,
'/game': wrap({
component: Game,
conditions: [checkLogin]
}),
'/spectator': wrap({
component: GameSpectator,
conditions: [checkLogin]
}),
'/ranking': wrap({
component: Ranking,
conditions: [checkLogin]
}),
'/profile': wrap({
component: ProfilePage,
conditions: [checkLogin]
}),
'/profile/*': wrap({
component: ProfilePage,
conditions: [checkLogin]
}),
'/unauthorized-access': UnauthorizedAccessPage,
'*': NotFound
};