Skip to content
Snippets Groups Projects
Commit 9e97eb0f authored by Yusuf Akgül's avatar Yusuf Akgül :hatching_chick:
Browse files

merged from main

parents c19fbd06 ad3f412d
No related branches found
No related tags found
1 merge request!6Sort + Search UI
Pipeline #34419 passed
Showing
with 235 additions and 209 deletions
...@@ -10,4 +10,8 @@ IGDB_IMG_BASE_URL="https://images.igdb.com/igdb/image/upload" ...@@ -10,4 +10,8 @@ IGDB_IMG_BASE_URL="https://images.igdb.com/igdb/image/upload"
# For Authentication # For Authentication
TWITCH_CLIENT_ID="imdb_client_id" TWITCH_CLIENT_ID="imdb_client_id"
TWITCH_CLIENT_SECRET="imdb_auth_id" TWITCH_CLIENT_SECRET="imdb_auth_id"
\ No newline at end of file
# For Clerk Authentication
NEXT_PUBLIC_CLERK_PUBLISHABLE_KEY="clerk_publishable_key"
CLERK_SECRET_KEY="clerk_secret_key"
\ No newline at end of file
...@@ -42,5 +42,4 @@ yarn-error.log* ...@@ -42,5 +42,4 @@ yarn-error.log*
next-env.d.ts next-env.d.ts
# prisma # prisma
/prisma/migrations/*
dev.db* dev.db*
\ No newline at end of file
...@@ -20,31 +20,40 @@ image: node:20 ...@@ -20,31 +20,40 @@ image: node:20
stages: # List of stages for jobs, and their order of execution stages: # List of stages for jobs, and their order of execution
- build - build
- test - test
- deploy # - deploy
build-job: # This job runs in the build stage, which runs first. build-job: # This job runs in the build stage, which runs first.
stage: build stage: build
script: script:
- npm i - echo "Building application..."
#- npm run build # needs automatic api key binding/refresh - npm install
- npm run build
- echo "Application successfully built."
unit-test-job: # This job runs in the test stage. unit-test-job: # This job runs in the test stage.
stage: test # It only starts when the job in the build stage completes successfully. stage: test # It only starts when the job in the build stage completes successfully.
script: script:
- echo "Running unit tests... This will take about 10 seconds." - echo "Running unit tests... This will take about 10 seconds."
- sleep 10 - sleep 1
- echo "Code coverage is 90%" - echo "Code coverage is 90%"
lint-test-job: # This job also runs in the test stage. lint-test-job: # This job also runs in the test stage.
stage: test # It can run at the same time as unit-test-job (in parallel). stage: test # It can run at the same time as unit-test-job (in parallel).
script: script:
- echo "Linting code... This will take about 10 seconds." - echo "Linting code... This will take about 10 seconds."
- sleep 10 - sleep 1
- echo "No lint issues found." - echo "No lint issues found."
deploy-job: # This job runs in the deploy stage. #deploy-job: # This job runs in the deploy stage.
stage: deploy # It only runs when *both* jobs in the test stage complete successfully. # stage: deploy # It only runs when *both* jobs in the test stage complete successfully.
environment: production # environment: production
script: # only:
- echo "Deploying application..." # - main
- echo "Application successfully deployed." # script:
# - echo "Deploying application..."
# - npm install --foreground-scripts # without this= error
# - npm install --global vercel
# - vercel pull --yes --environment=production --token=$VERCEL_TOKEN
# - vercel build --prod --token=$VERCEL_TOKEN
# - vercel deploy --prebuilt --prod --token=$VERCEL_TOKEN
# - echo "Application successfully deployed."
# project_ss23 # project_ss23_gameunity
## Projektbeschreibung ## Projektbeschreibung
Unsere Idee ist es eine Social Media Plattform zu erstellen. Auf dieser Webseite soll es möglich Unsere Idee ist es eine Social Media Plattform zu erstellen. Auf dieser Webseite soll es möglich
......
import { SignIn } from "@clerk/nextjs";
export default function Login() { export default function Login() {
return ( return <SignIn />;
<div>
<h1>Login WIP</h1>
</div>
)
} }
\ No newline at end of file
import { SignUp } from "@clerk/nextjs";
export default function Signup() { export default function Signup() {
return ( return <SignUp />;
<div>
<h1>Signup WIP</h1>
</div>
)
} }
\ No newline at end of file
import { getGame, getGames } from "@/lib/igdb"; import { getGame, getGames } from "@/lib/igdb";
import { IGame } from "@/types/types"; import { IGame } from "@/types/igdb-types";
import Image from "next/image"; import Image from "next/image";
// renders a single game detail page // renders a single game detail page
...@@ -10,17 +10,8 @@ export default async function GameDetail({ params }: { params: { gameid: string ...@@ -10,17 +10,8 @@ export default async function GameDetail({ params }: { params: { gameid: string
<div> <div>
<h1>Game Detail</h1> <h1>Game Detail</h1>
<h1>{data[0].name}</h1> <h1>{data[0].name}</h1>
<Image src={data[0].cover.url} alt={data[0].name} width={264} height={374} priority={true} /> <Image src={data[0].cover.url} alt={data[0].name} width={264} height={374} priority={true} style={{ width: 'auto', height: 'auto' }} />
<p>{data[0].summary}</p> <p>{data[0].summary}</p>
</div> </div>
) )
}
// pre-renders static paths for all fetched games for faster page loads
export async function generateStaticParams() {
const games = await getGames()
return games.map((game) => ({
gameid: game.id.toString(),
}));
} }
\ No newline at end of file
"use client" "use client"
import Dashboard from "@/components/Dashboard";
import Sort from "@/components/Sort";
import { Grid, Hidden } from "@mui/material";
export default function DashboardLayout({ export default function DashboardLayout({
children, children,
}: { }: {
...@@ -11,21 +7,9 @@ export default function DashboardLayout({ ...@@ -11,21 +7,9 @@ export default function DashboardLayout({
}) { }) {
return ( return (
<section> <section>
<Grid container spacing={2}> <div>
<Grid item xs={2}> {children}
<Dashboard /> </div>
</Grid>
<Grid item xs={10} md={8}>
{children}
</Grid>
<Hidden mdDown>
<Grid item xs={2}>
<Sort />
</Grid>
</Hidden>
</Grid>
</section> </section>
); );
} }
\ No newline at end of file
"use client" import { InfiniteScrollGames } from "@/components/InfiniteScroll";
import Game from "@/components/Game";
import Search from "@/components/Search";
import { getBaseURL } from "@/lib/utils";
import { IGame } from "@/types/types";
import { Card, CardContent, Grid, Stack } from "@mui/material";
import { Fragment } from "react";
import InfiniteScroll from "react-infinite-scroll-component";
import { useInfiniteQuery } from "react-query";
// renders a list of games infinitely (presumably) // renders a list of games infinitely (presumably)
export default function GamesPage() { export default async function GamesPage() {
const {
data,
error,
fetchNextPage,
hasNextPage,
isFetching,
isFetchingNextPage,
status,
} = useInfiniteQuery(
'infiniteGames',
async ({ pageParam = 1 }) =>
await fetch(
`${getBaseURL()}/api/games/?page=${pageParam}`,
{ cache: 'force-cache', }
).then((result) => result.json() as Promise<IGame[]>),
{
getNextPageParam: (lastPage, pages) => {
return lastPage.length > 0 ? pages.length + 1 : undefined;
},
}
);
return ( return (
<Stack spacing={2}> <div className="py-5">
<Search /> <InfiniteScrollGames />
<Card> </div>
<CardContent>
{status === 'success' && (
<InfiniteScroll
dataLength={data?.pages.length * 20}
next={fetchNextPage}
hasMore={hasNextPage ? true : false}
loader={<h4>Loading...</h4>}
endMessage={
<p style={{ textAlign: 'center' }}>
<b>Yay! You have seen it all</b>
</p>
}
>
<Grid container spacing={2} justifyContent="center">
{data?.pages.map((page, i) => (
<Fragment key={i}>
{page.map((game: IGame) => (
<Grid item xs={12} ss={6} sm={4} md={3} lg={2} key={game.id}>
<Game id={game.id} name={game.name} cover={game.cover} key={game.id} />
</Grid>
))}
</Fragment>
))}
</Grid>
</InfiniteScroll>
)}
</CardContent>
</Card>
</Stack>
) )
} }
\ No newline at end of file
import PostMessageForm from "@/components/PostMessageForm"; import PostMessageForm from "@/components/PostMessageForm";
import { prisma } from "@/prisma/db"; import { prisma } from "@/prisma/db";
export default async function ThreadsPage() { export default async function HomePage() {
let messages = null let messages = null
try { try {
messages = await prisma.message.findMany() messages = await prisma.message.findMany()
...@@ -11,7 +11,8 @@ export default async function ThreadsPage() { ...@@ -11,7 +11,8 @@ export default async function ThreadsPage() {
return ( return (
<div> <div>
<h1>Threads WIP</h1> <h1>Home WIP</h1>
<p>This will be where all messages show up.</p>
<p>Needs a reload after posting!!</p> <p>Needs a reload after posting!!</p>
{messages ? {messages ?
......
import { UserProfile } from "@clerk/nextjs";
import { dark } from '@clerk/themes';
export default function User({ params }: { params: { userid: string } }) { export default function User({ params }: { params: { userid: string } }) {
return ( return (
<div> <>
<h1>User Profile Page WIP</h1> <h1>User Profile Page WIP</h1>
<p>Unique UserName: {params.userid}</p> <p>Unique Page Params: {params.userid}</p>
</div> <UserProfile appearance={{ baseTheme: dark }} />
</>
) )
} }
\ No newline at end of file
export default function Friends() { export default function Followers() {
return ( return (
<div> <div>
<h1>Friends Page WIP</h1> <h1>Followers Page WIP</h1>
</div> </div>
) )
} }
\ No newline at end of file
export default function BlogsPage() { export default function Help() {
return ( return (
<div> <div>
<h1>Blog WIP</h1> <h1>Help Page WIP</h1>
</div> </div>
) )
} }
\ No newline at end of file
import DashboardNav from "@/components/nav"
import { SiteFooter } from "@/components/site-footer"
import { dashboardConfig } from "@/lib/config/dashboard"
interface DashboardLayoutProps {
children?: React.ReactNode
}
export default async function ContentLayout({
children,
}: DashboardLayoutProps) {
return (
<div className="flex min-h-screen flex-col space-y-6">
<div className="container grid flex-1 gap-12 md:grid-cols-[200px_1fr]">
<aside className="hidden w-[200px] flex-col md:flex">
<div className="sticky top-0">
<DashboardNav items={dashboardConfig.sidebarNav} />
</div>
</aside>
<main className="flex w-full flex-1 flex-col overflow-hidden">
{children}
</main>
</div>
<SiteFooter className="border-t" />
</div>
)
}
\ No newline at end of file
...@@ -3,6 +3,10 @@ import { NextRequest, NextResponse } from "next/server"; ...@@ -3,6 +3,10 @@ import { NextRequest, NextResponse } from "next/server";
export async function GET(req: NextRequest) { export async function GET(req: NextRequest) {
const p = req.nextUrl.searchParams; const p = req.nextUrl.searchParams;
const games = await getGames(p.get('page') ? parseInt(p.get('page') as string) : undefined); try {
return NextResponse.json(games); const games = await getGames(p.get('page') ? parseInt(p.get('page') as string) : undefined);
return NextResponse.json(games);
} catch (error) {
return NextResponse.json(error, { status: 500 });
}
} }
\ No newline at end of file
File moved
@tailwind base;
@tailwind components;
@tailwind utilities;
@layer base {
:root {
--background: 0 0% 100%;
--foreground: 222.2 47.4% 11.2%;
--muted: 210 40% 96.1%;
--muted-foreground: 215.4 16.3% 46.9%;
--popover: 0 0% 100%;
--popover-foreground: 222.2 47.4% 11.2%;
--card: 0 0% 100%;
--card-foreground: 222.2 47.4% 11.2%;
--border: 214.3 31.8% 91.4%;
--input: 214.3 31.8% 91.4%;
--primary: 222.2 47.4% 11.2%;
--primary-foreground: 210 40% 98%;
--secondary: 210 40% 96.1%;
--secondary-foreground: 222.2 47.4% 11.2%;
--accent: 210 40% 96.1%;
--accent-foreground: 222.2 47.4% 11.2%;
--destructive: 0 100% 50%;
--destructive-foreground: 210 40% 98%;
--ring: 215 20.2% 65.1%;
--radius: 0.5rem;
}
.dark {
--background: 224 71% 4%;
--foreground: 213 31% 91%;
--muted: 223 47% 11%;
--muted-foreground: 215.4 16.3% 56.9%;
--popover: 224 71% 4%;
--popover-foreground: 215 20.2% 65.1%;
--card: 224 71% 4%;
--card-foreground: 213 31% 91%;
--border: 216 34% 17%;
--input: 216 34% 17%;
--primary: 210 40% 98%;
--primary-foreground: 222.2 47.4% 1.2%;
--secondary: 222.2 47.4% 11.2%;
--secondary-foreground: 210 40% 98%;
--accent: 216 34% 17%;
--accent-foreground: 210 40% 98%;
--destructive: 0 63% 31%;
--destructive-foreground: 210 40% 98%;
--ring: 216 34% 17%;
--radius: 0.5rem;
}
}
@layer base {
* {
@apply border-border;
}
body {
@apply bg-background text-foreground;
font-feature-settings: "rlig" 1, "calt" 1;
}
}
\ No newline at end of file
"use client" import { Inter } from 'next/font/google'
import './globals.css'
import { Container, CssBaseline, ThemeProvider } from "@mui/material" import Providers from '@/components/react-query/provider'
import { createContext, useState } from "react" import SiteLoad from '@/components/site-loading'
import { QueryClient, QueryClientProvider } from "react-query" import { ThemeProvider } from '@/components/ui/theme-provider'
import Header from "../components/Header" import { ClerkProvider } from '@clerk/nextjs'
import { Theme } from "./theme" import { Suspense } from 'react'
const inter = Inter({ subsets: ['latin'] })
// metadata for the website
export const metadata = { export const metadata = {
title: 'GameUnity', title: 'Create Next App',
description: 'Soon', description: 'Generated by create next app',
} }
// for dark mode global context
export const ColorModeContext = createContext({ toggleColorMode: () => { } });
// this is the root layout for all pages ({children})
export default function RootLayout({ export default function RootLayout({
children, children,
}: { }: {
children: React.ReactNode children: React.ReactNode
}) { }) {
const [queryClient] = useState(() => new QueryClient());
const [theme, colorMode] = Theme();
return ( return (
<html lang="en"> <html lang="en" suppressHydrationWarning>
<QueryClientProvider client={queryClient}> <head />
<ColorModeContext.Provider value={colorMode}> <body className={inter.className}>
<ThemeProvider theme={theme}> <ThemeProvider attribute="class" defaultTheme="system" enableSystem>
<CssBaseline /> <Suspense fallback={<SiteLoad />}>
<body> <ClerkProvider>
<Container maxWidth={false}> <Providers>
<Header />
{children} {children}
</Container> </Providers>
</body> </ClerkProvider>
</ThemeProvider> </Suspense>
</ColorModeContext.Provider> </ThemeProvider>
</QueryClientProvider> </body>
</html> </html>
) )
}
// custom super small breakpoint for responsive design
declare module '@mui/material/styles' {
interface BreakpointOverrides {
ss: true;
}
} }
\ No newline at end of file
import Link from "next/link"; import { buttonVariants } from '@/components/ui/button'
import { cn } from '@/lib/utils'
import Link from 'next/link'
// renders home page
export default function Home() { export default function Home() {
return ( return (
<main> <>
<div> <section className="space-y-6 pb-8 pt-6 md:pb-12 md:pt-10 lg:py-32">
<h1>Welcome to GameUnity!</h1> <div className="container flex max-w-[64rem] flex-col items-center gap-4 text-center">
<p>This will be our Home Page and is still WIP</p> <h1 className="font-heading text-3xl sm:text-5xl md:text-6xl lg:text-7xl">
<Link href="/games">Games List Progress</Link> Welcome to GameUnity!
</div> </h1>
</main> <p className="max-w-[42rem] leading-normal text-muted-foreground sm:text-xl sm:leading-8">
This will be our Home Page and is still WIP
</p>
<div className="space-x-4">
<Link href="/login" className={cn(buttonVariants({ size: "lg" }))}>
Log In
</Link>
<Link href="/signup" className={cn(buttonVariants({ size: "lg" }))}>
Sign Up
</Link>
</div>
<div className="flex flex-col space-y-4">
<Link href="/games" className={cn(buttonVariants({ size: "lg" }))}>
Games List Progress
</Link>
<Link href="/home" className={cn(buttonVariants({ size: "lg" }))}>
Home List Progress
</Link>
</div>
</div>
</section>
</>
) )
} }
\ No newline at end of file
import { Theme, createTheme } from "@mui/material";
import { useMemo, useState } from "react";
// this is the main theme for the website
export function Theme(): [Theme, { toggleColorMode: () => void }] {
const [mode, setMode] = useState<'light' | 'dark'>('dark');
const colorMode = useMemo(
() => ({
toggleColorMode: () => {
setMode((prevMode) => (prevMode === 'dark' ? 'light' : 'dark'));
},
}),
[],
);
return [useMemo(() =>
createTheme({
palette: {
mode: mode,
},
breakpoints: {
values: {
xs: 0,
ss: 300,
sm: 600,
md: 900,
lg: 1200,
xl: 1536,
},
},
}),
[mode],
),
colorMode];
}
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment