Skip to content

Commit 656f4ac

Browse files
authored
Merge pull request #183 from wlmac/develop
Develop
2 parents 1d9b596 + 7c33b7b commit 656f4ac

File tree

19 files changed

+140
-74
lines changed

19 files changed

+140
-74
lines changed

public/resources/static/css/base.css

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -422,6 +422,17 @@ blockquote {
422422
list-style-type: inherit;
423423
}
424424

425+
.deleted-notif{
426+
background-color: var(--status-red);
427+
text-align: center;
428+
padding: 0.5em;
429+
}
430+
431+
.deleted-notif span{
432+
color: white;
433+
font-size: 1.25em;
434+
}
435+
425436
@media screen and (display-mode: standalone) {
426437
#back {
427438
display: flex;

public/resources/static/css/profile/update.css

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,8 @@
1+
:root{
2+
--delete-light: #c22727;
3+
--delete-dark: #960000;
4+
}
5+
16
label {
27
font-size: 14px;
38
}
@@ -28,3 +33,42 @@ label {
2833
button {
2934
margin: 1rem 0;
3035
}
36+
37+
.delete {
38+
background-color: var(--delete-light) !important;
39+
}
40+
41+
.delete:hover{
42+
background-color: var(--delete-dark) !important;
43+
}
44+
45+
.delete-container{
46+
border: solid var(--status-red) 2px;
47+
padding: 2em;
48+
}
49+
50+
.delete-title{
51+
margin-top: 0;
52+
}
53+
54+
.delete-confirmation{
55+
position: fixed;
56+
left: 0;
57+
right: 0;
58+
top: 0;
59+
bottom: 0;
60+
transition: all .2s;
61+
}
62+
63+
.delete-confirmation .delete-box{
64+
padding: 1em;
65+
margin: auto;
66+
background-color: white;
67+
border: solid var(--status-red) 2px;
68+
border-radius: 10px;
69+
box-shadow: 3px 3px 5px;
70+
}
71+
72+
.delete-confirmation span{
73+
height: fit-content;
74+
}

src/components/account/profile/edit/index.tsx

Lines changed: 32 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -21,15 +21,17 @@ export const ProfileEdit = (): JSX.Element => {
2121
const nav: NavigateFunction = useNavigate();
2222

2323
const session: Session = React.useContext(SessionContext);
24+
const [showDelete, setShowDelete] = React.useState<boolean>(false);
2425
let user: User = session.user;
2526

2627
// Form
2728
const { register, handleSubmit, watch, reset, formState: { errors } } = useForm<Inputs>();
2829

2930
React.useEffect(() => {
31+
// console.log(user)
3032
if ("username" in user) {
31-
console.log("User:", { ...session.user, graduating_year: session.user.graduating_year!.toString() });
32-
reset({ ...session.user, graduating_year: session.user.graduating_year!.toString() });
33+
// console.log("User:", { ...session.user, graduating_year: session.user.graduating_year?.toString() });
34+
reset({ ...session.user, graduating_year: session.user.graduating_year?.toString() });
3335
}
3436
}, [session.user]);
3537

@@ -42,6 +44,15 @@ export const ProfileEdit = (): JSX.Element => {
4244
});
4345
}
4446

47+
const deleteUser = () => {
48+
session.request('post', `${Routes.USER}/me/delete`).then((res) => {
49+
if(res.status === 200){
50+
session.refreshUser();
51+
nav(`/user/${user.username}`)
52+
}
53+
})
54+
}
55+
4556
// console.log(watch("graduating_year")) // watch input value by passing the name of it
4657
// console.log(user.timezone);
4758

@@ -955,13 +966,13 @@ export const ProfileEdit = (): JSX.Element => {
955966

956967
<div className="field">
957968
<div className="label"><label htmlFor="id_first_name">First name:</label></div>
958-
<span><input {...register("first_name")} type="text" name="first_name" value="Jimmy" maxLength={150} id="id_first_name" /><div data-lastpass-icon-root="true" style={{ position: "relative", height: "0px", width: "0px", float: "left" }}><template><svg width="24" height="24" viewBox="0 0 24 24" fill="none" data-lastpass-icon="true" style={{ position: "absolute", cursor: "pointer", height: "22px", maxHeight: "22px", width: "22px", maxWidth: "22px", top: "11.5px", left: "154px", zIndex: "auto", color: "rgb(215, 64, 58)" }}><rect x="0.680176" y="0.763062" width="22.6392" height="22.4737" rx="4" fill="currentColor"></rect><path fill-rule="evenodd" clip-rule="evenodd" d="M19.7935 7.9516C19.7935 7.64414 20.0427 7.3949 20.3502 7.3949C20.6576 7.3949 20.9069 7.64414 20.9069 7.9516V16.0487C20.9069 16.3562 20.6576 16.6054 20.3502 16.6054C20.0427 16.6054 19.7935 16.3562 19.7935 16.0487V7.9516Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M4.76288 13.6577C5.68525 13.6577 6.43298 12.9154 6.43298 11.9998C6.43298 11.0842 5.68525 10.3419 4.76288 10.3419C3.8405 10.3419 3.09277 11.0842 3.09277 11.9998C3.09277 12.9154 3.8405 13.6577 4.76288 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M10.3298 13.6577C11.2521 13.6577 11.9999 12.9154 11.9999 11.9998C11.9999 11.0842 11.2521 10.3419 10.3298 10.3419C9.4074 10.3419 8.65967 11.0842 8.65967 11.9998C8.65967 12.9154 9.4074 13.6577 10.3298 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M15.8964 13.6577C16.8188 13.6577 17.5665 12.9154 17.5665 11.9998C17.5665 11.0842 16.8188 10.3419 15.8964 10.3419C14.974 10.3419 14.2263 11.0842 14.2263 11.9998C14.2263 12.9154 14.974 13.6577 15.8964 13.6577Z" fill="white"></path></svg></template></div></span>
969+
<span><input {...register("first_name")} type="text" name="first_name" value={`${user?.first_name}`} maxLength={150} id="id_first_name" /><div data-lastpass-icon-root="true" style={{ position: "relative", height: "0px", width: "0px", float: "left" }}><template><svg width="24" height="24" viewBox="0 0 24 24" fill="none" data-lastpass-icon="true" style={{ position: "absolute", cursor: "pointer", height: "22px", maxHeight: "22px", width: "22px", maxWidth: "22px", top: "11.5px", left: "154px", zIndex: "auto", color: "rgb(215, 64, 58)" }}><rect x="0.680176" y="0.763062" width="22.6392" height="22.4737" rx="4" fill="currentColor"></rect><path fill-rule="evenodd" clip-rule="evenodd" d="M19.7935 7.9516C19.7935 7.64414 20.0427 7.3949 20.3502 7.3949C20.6576 7.3949 20.9069 7.64414 20.9069 7.9516V16.0487C20.9069 16.3562 20.6576 16.6054 20.3502 16.6054C20.0427 16.6054 19.7935 16.3562 19.7935 16.0487V7.9516Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M4.76288 13.6577C5.68525 13.6577 6.43298 12.9154 6.43298 11.9998C6.43298 11.0842 5.68525 10.3419 4.76288 10.3419C3.8405 10.3419 3.09277 11.0842 3.09277 11.9998C3.09277 12.9154 3.8405 13.6577 4.76288 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M10.3298 13.6577C11.2521 13.6577 11.9999 12.9154 11.9999 11.9998C11.9999 11.0842 11.2521 10.3419 10.3298 10.3419C9.4074 10.3419 8.65967 11.0842 8.65967 11.9998C8.65967 12.9154 9.4074 13.6577 10.3298 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M15.8964 13.6577C16.8188 13.6577 17.5665 12.9154 17.5665 11.9998C17.5665 11.0842 16.8188 10.3419 15.8964 10.3419C14.974 10.3419 14.2263 11.0842 14.2263 11.9998C14.2263 12.9154 14.974 13.6577 15.8964 13.6577Z" fill="white"></path></svg></template></div></span>
959970
</div>
960971

961972

962973
<div className="field">
963974
<div className="label"><label htmlFor="id_last_name">Last name:</label></div>
964-
<span><input {...register("last_name")} type="text" name="last_name" value="Liu" maxLength={150} id="id_last_name" /><div data-lastpass-icon-root="true" style={{ position: "relative", height: "0px", width: "0px", float: "left" }}><template><svg width="24" height="24" viewBox="0 0 24 24" fill="none" data-lastpass-icon="true" style={{ position: "absolute", cursor: "pointer", height: "22px", maxHeight: "22px", width: "22px", maxWidth: "22px", top: "11.5px", left: "154px", zIndex: "auto", color: "rgb(215, 64, 58)" }}><rect x="0.680176" y="0.763062" width="22.6392" height="22.4737" rx="4" fill="currentColor"></rect><path fill-rule="evenodd" clip-rule="evenodd" d="M19.7935 7.9516C19.7935 7.64414 20.0427 7.3949 20.3502 7.3949C20.6576 7.3949 20.9069 7.64414 20.9069 7.9516V16.0487C20.9069 16.3562 20.6576 16.6054 20.3502 16.6054C20.0427 16.6054 19.7935 16.3562 19.7935 16.0487V7.9516Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M4.76288 13.6577C5.68525 13.6577 6.43298 12.9154 6.43298 11.9998C6.43298 11.0842 5.68525 10.3419 4.76288 10.3419C3.8405 10.3419 3.09277 11.0842 3.09277 11.9998C3.09277 12.9154 3.8405 13.6577 4.76288 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M10.3298 13.6577C11.2521 13.6577 11.9999 12.9154 11.9999 11.9998C11.9999 11.0842 11.2521 10.3419 10.3298 10.3419C9.4074 10.3419 8.65967 11.0842 8.65967 11.9998C8.65967 12.9154 9.4074 13.6577 10.3298 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M15.8964 13.6577C16.8188 13.6577 17.5665 12.9154 17.5665 11.9998C17.5665 11.0842 16.8188 10.3419 15.8964 10.3419C14.974 10.3419 14.2263 11.0842 14.2263 11.9998C14.2263 12.9154 14.974 13.6577 15.8964 13.6577Z" fill="white"></path></svg></template></div></span>
975+
<span><input {...register("last_name")} type="text" name="last_name" value={`${user?.last_name}`} maxLength={150} id="id_last_name" /><div data-lastpass-icon-root="true" style={{ position: "relative", height: "0px", width: "0px", float: "left" }}><template><svg width="24" height="24" viewBox="0 0 24 24" fill="none" data-lastpass-icon="true" style={{ position: "absolute", cursor: "pointer", height: "22px", maxHeight: "22px", width: "22px", maxWidth: "22px", top: "11.5px", left: "154px", zIndex: "auto", color: "rgb(215, 64, 58)" }}><rect x="0.680176" y="0.763062" width="22.6392" height="22.4737" rx="4" fill="currentColor"></rect><path fill-rule="evenodd" clip-rule="evenodd" d="M19.7935 7.9516C19.7935 7.64414 20.0427 7.3949 20.3502 7.3949C20.6576 7.3949 20.9069 7.64414 20.9069 7.9516V16.0487C20.9069 16.3562 20.6576 16.6054 20.3502 16.6054C20.0427 16.6054 19.7935 16.3562 19.7935 16.0487V7.9516Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M4.76288 13.6577C5.68525 13.6577 6.43298 12.9154 6.43298 11.9998C6.43298 11.0842 5.68525 10.3419 4.76288 10.3419C3.8405 10.3419 3.09277 11.0842 3.09277 11.9998C3.09277 12.9154 3.8405 13.6577 4.76288 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M10.3298 13.6577C11.2521 13.6577 11.9999 12.9154 11.9999 11.9998C11.9999 11.0842 11.2521 10.3419 10.3298 10.3419C9.4074 10.3419 8.65967 11.0842 8.65967 11.9998C8.65967 12.9154 9.4074 13.6577 10.3298 13.6577Z" fill="white"></path><path fill-rule="evenodd" clip-rule="evenodd" d="M15.8964 13.6577C16.8188 13.6577 17.5665 12.9154 17.5665 11.9998C17.5665 11.0842 16.8188 10.3419 15.8964 10.3419C14.974 10.3419 14.2263 11.0842 14.2263 11.9998C14.2263 12.9154 14.974 13.6577 15.8964 13.6577Z" fill="white"></path></svg></template></div></span>
965976
</div>
966977

967978

@@ -983,10 +994,25 @@ export const ProfileEdit = (): JSX.Element => {
983994
<!-- </span> -->
984995
<!-- </div> --> */}
985996
<div style={{ display: "flex", alignItems: "center", "gap": "3px" }}>
986-
<button type="submit" className="btn">Submit</button>
987-
<NavLink to={`/user/${user.username}`} className="btn" role="button" aria-pressed="true">Cancel</NavLink>
997+
<button type="submit" className="btn btn-primary">Submit</button>
998+
<NavLink to={`/user/${user.username}`} className="btn btn-primary" role="button" aria-pressed="true">Cancel</NavLink>
988999
</div>
9891000
</form>
1001+
<br />
1002+
{!session.user.is_deleted && <div className="delete-container">
1003+
<h2 className="delete-title">Danger Zone</h2>
1004+
<button className="delete btn-small btn-primary" style={{width: "100%"}} onClick={() => setShowDelete(true)}>Delete User</button>
1005+
</div>}
1006+
1007+
<div className="delete-confirmation" style={{display: "flex", flexDirection: "column", justifyContent: "center", visibility: showDelete ? "visible" : "hidden", opacity: showDelete ? "100%" : "0%"}} >
1008+
<div className="delete-box" style={{display: "flex", flexDirection: "column"}}>
1009+
<h3>Are you sure you want to delete this user?</h3>
1010+
<span style={{display: "flex", flexDirection: "row", justifyContent: "right"}}>
1011+
<button className="delete btn-small btn-primary" onClick={deleteUser}>YES</button>
1012+
<button className="btn btn-small btn-primary" onClick={() => setShowDelete(false)}>No</button>
1013+
</span>
1014+
</div>
1015+
</div>
9901016
</div>
9911017
</>
9921018
);

src/components/account/profile/index.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ export const Profile = (props: { children?: JSX.Element }): JSX.Element => {
1212
return (
1313
<LoginRequired>
1414
<>
15+
<meta name="robots" content="noindex"></meta>
1516
<link rel="stylesheet" href="/resources/static/css/profile/detail.css" />
1617
<link rel="stylesheet" href="/resources/static/css/secondary.css" />
1718
<div className="container">

src/components/account/profile/my-profile/index.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import { NavigateFunction, useNavigate } from "react-router-dom";
55
// Login Required
66
export const MyProfile = (): JSX.Element => {
77
const session: Session = React.useContext(SessionContext);
8+
console.log(session)
89
const nav: NavigateFunction = useNavigate();
910

1011
React.useEffect(() => {

src/components/announcements/index.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import Organization from "../../util/core/interfaces/organization";
88
import MembershipStatus from "../../util/core/misc/membership";
99
import Media from "../../util/core/misc/media";
1010
import Tag from "../../util/core/interfaces/tag";
11-
import { getTags, TagElement, DeletableTagElement } from "../../util/core/tags";
11+
import { TagElement, DeletableTagElement } from "../../util/core/tags";
1212
import { Session, SessionContext, User } from "../../util/core/session";
1313
import UserField from '../../util/core/interfaces/post';
1414
import Routes from "../../util/core/misc/routes";
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
import * as React from "react";
2+
3+
export const DeletionNotification = (props: {onRestore: ()=>void}): JSX.Element => {
4+
return <div style={{display: "flex", flexDirection: "row", justifyContent: "center", alignItems: "center", gap: "10px"}} className="deleted-notif">
5+
<span>WARNING: Account will soon be deleted</span>
6+
<button className="btn btn-primary" onClick={props.onRestore}>Restore</button>
7+
</div>
8+
}

src/components/app/index.tsx

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,9 @@ import { Theme, ThemeContext, ThemeProvider } from '../../util/core/client/theme
3434
import { NewCourse } from "../account/timetable/edit/new-course";
3535
import { LoginRequired } from "../../util/login-required";
3636
import { MyProfile } from "../account/profile/my-profile";
37+
import { DeletionNotification } from "./delete-component";
38+
39+
import * as URLRoutes from "../../util/core/misc/routes";
3740

3841
export const _App = (): JSX.Element => {
3942
const nav: NavigateFunction = useNavigate();
@@ -49,11 +52,21 @@ export const _App = (): JSX.Element => {
4952
window.scrollTo(0, 0);
5053
}, [location]);
5154

55+
const onRestore = (): void => {
56+
session.request('post', `${URLRoutes.default.USER}/me/restore`).then((res) => {
57+
session.refreshUser();
58+
window.location.reload();
59+
}).catch((err) => {
60+
alert("failed to restore account - please contact us!")
61+
})
62+
}
63+
5264
return (
5365
<>
5466
<link rel="stylesheet" href={theme.bannerPath} />
5567
<link rel="stylesheet" href={theme.palettePath} />
5668
<div className="page" style={{backgroundColor: "white"}}>
69+
{session.user?.is_deleted ? <DeletionNotification onRestore={onRestore} /> : <></>}
5770
<NavigationBar />
5871

5972
<div className="router-outlet">

src/components/app/navigation/index.tsx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import { Link, NavigateFunction, useNavigate } from "react-router-dom";
44
import { getToken, loggedIn, logout } from "../../../util/core/AuthService";
55
import { Session, SessionContext } from "../../../util/core/session";
66
import { Theme, ThemeContext } from "../../../util/core/client/theme/ThemeContext";
7+
import Routes from "../../../util/core/misc/routes";
78

89
export const NavigationBar = (): JSX.Element => {
910
const nav: NavigateFunction = useNavigate();
@@ -66,6 +67,7 @@ export const NavigationBar = (): JSX.Element => {
6667
<>
6768
<li><NavLink href={`/user/${session.user.username}`} className="sidenav-close">Profile</NavLink></li>
6869
<li><NavLink href={`/timetable`} className="sidenav-close">Timetable</NavLink></li>
70+
{(session.user?.is_superuser || session.user?.organizations_leading && session.user?.organizations_leading?.length > 0 || session.user?.organizations_supervising && session.user?.organizations_supervising?.length > 0) && <li tabIndex={0}><a href={`${Routes.BASEURL}/admin/`}>Admin</a></li>}
6971
<li><a className="nav-link" onClick={(ev: React.MouseEvent) => {
7072
ev.preventDefault();
7173
logout();
@@ -143,7 +145,7 @@ export const NavigationBar = (): JSX.Element => {
143145
<ul id="dropdownAcc" className="dropdown-content" tabIndex={0}>
144146
<li tabIndex={0}><Link to={`/user/${session.user.username}`}>Profile</Link></li>
145147
<li tabIndex={0}><Link to="/timetable">Timetable</Link></li>
146-
{session.user.is_staff && <li tabIndex={0}><a href="/admin/">Admin</a></li>}
148+
{(session.user?.is_superuser || session.user?.organizations_leading && session.user?.organizations_leading?.length > 0 || session.user?.organizations_supervising && session.user?.organizations_supervising?.length > 0) && <li tabIndex={0}><a href={`${Routes.BASEURL}/admin/`}>Admin</a></li>}
147149
<li tabIndex={0}><Link to="/account/logout">Logout</Link></li>
148150
</ul>
149151
</>

src/components/blog/details/index.tsx

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import { dateFormat } from "../../../util/core/misc/date";
1212
import { TagElement } from "../../../util/core/tags";
1313
import { loggedIn } from "../../../util/core/AuthService";
1414
import { NotFound } from "../../notfound";
15+
import { cleanUrl } from "../../../util/core/misc/tools";
1516

1617
export const BlogDetails = (): JSX.Element => {
1718
const { slug } = useParams();
@@ -34,7 +35,7 @@ export const BlogDetails = (): JSX.Element => {
3435
<link rel="stylesheet" href="/resources/static/css/blog-detail.css" />
3536
<div className="container">
3637
<div className="card-container">
37-
<img className="card-image" src={post.featured_image+"?w=800&fmt=webp"} />
38+
<img className="card-image" src={cleanUrl(post.featured_image)} />
3839
<div className="tag-section">
3940
{
4041
tags.map((tag: Tag) => {

src/components/blog/index.tsx

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,10 +9,11 @@ import Media from "../../util/core/misc/media";
99
import MembershipStatus from "../../util/core/misc/membership";
1010
import Routes from "../../util/core/misc/routes";
1111
import { Session, SessionContext, User } from "../../util/core/session";
12-
import { getTags, TagElement } from "../../util/core/tags";
12+
import { TagElement } from "../../util/core/tags";
1313
import Markdown, { markdownToPlainText } from "../markdown";
1414
import { loggedIn } from "../../util/core/AuthService";
1515
import { dateFormat } from "../../util/core/misc/date";
16+
import { cleanUrl } from "../../util/core/misc/tools";
1617

1718
const BLOG_FETCHLIMIT = 10; // how many anns to fetch each api request
1819

@@ -119,7 +120,7 @@ const BlogPostElement = (props: { post: BlogPost, tags: Array<Tag> }): JSX.Eleme
119120
<>
120121
<div className="card">
121122
<div className="card-headers">
122-
<img className="card-image" src={post.featured_image+"?w=800&fmt=webp"} />
123+
<img className="card-image" src={cleanUrl(post.featured_image)} />
123124
<div className="card-text">
124125
<div className="tag-section">
125126
{

0 commit comments

Comments
 (0)