diff --git a/src/components/MemberCard.astro b/src/components/MemberCard.astro
new file mode 100644
index 0000000..f79bb9d
--- /dev/null
+++ b/src/components/MemberCard.astro
@@ -0,0 +1,24 @@
+---
+// Import the global.css file here so that it is included on
+// all pages through the use of the component.
+import "../styles/global.css"
+const { member } = Astro.props
+---
+
+
+
+
+ {
+ member.avatar ? (
+

+ ) : (
+

+ )
+ }
+
+
+
+
{member.alias}
+
{member.profile}
+
+
diff --git a/src/pages/about.astro b/src/pages/about.astro
index aaf4ed3..d3ac08b 100644
--- a/src/pages/about.astro
+++ b/src/pages/about.astro
@@ -1,36 +1,54 @@
---
import BaseLayout from "../layouts/BaseLayout.astro"
+import { computed } from "vue"
+import MemberCard from "../components/MemberCard.astro"
-const members = await fetch("https://api.nbtca.space/v2/members").then(res => {
+const members: {
+ memberId: string
+ alias: string
+ avatar: string
+ profile: string
+}[] = await fetch("https://api.nbtca.space/v2/members").then(res => {
return res.json()
})
+
+// memberId is like "3232323233", the second and third number is the year of the member
+const memberGroupByYear = computed(() => {
+ const group = members
+ // TODO delete the test member
+ .filter(member => member.memberId != "0000000000" && member.memberId != "2333333333")
+ .reduce((acc, cur) => {
+ const year = parseInt("20" + cur.memberId.slice(1, 3))
+ if (!acc[year]) {
+ acc[year] = []
+ }
+ acc[year].push(cur)
+ return acc
+ }, {} as Record)
+ return group
+})
---
协会成员
-
+
{
- members.map(member => {
- return (
-
-
-
- {member.avatar ? (
-

- ) : (
-

- )}
+ Object.keys(memberGroupByYear.value)
+ .sort((a, b) => parseInt(b) - parseInt(a))
+ .map(year => {
+ return (
+
+
{year}
+
+ {memberGroupByYear.value[year].map(member => (
+
+ ))}
-
-
{member.alias}
-
{member.profile}
-
-
- )
- })
+ )
+ })
}