diff --git a/.env b/.env
new file mode 100644
index 0000000..e4bc77a
--- /dev/null
+++ b/.env
@@ -0,0 +1 @@
+EXPO_PUBLIC_GRAPQL_API_KEY = thataluna::local.net+1000::9e3d19bf6be3f41ed9e4208656794ca97d47a2c3eb6d75167918892ddc692607
\ No newline at end of file
diff --git a/api/curl/index.graphql b/api/exercises/index.graphql
similarity index 100%
rename from api/curl/index.graphql
rename to api/exercises/index.graphql
diff --git a/api/index.graphql b/api/index.graphql
index d1aab5f..1d20e09 100644
--- a/api/index.graphql
+++ b/api/index.graphql
@@ -1,3 +1,3 @@
-schema @sdl(files: ["curl/index.graphql"]) {
+schema @sdl(files: ["exercises/index.graphql"]) {
query: Query
}
diff --git a/package-lock.json b/package-lock.json
index 3b5d5a1..6ae7a9d 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -8,11 +8,15 @@
"name": "workoutapp",
"version": "1.0.0",
"dependencies": {
+ "@tanstack/react-query": "^5.49.2",
"expo": "~51.0.17",
"expo-constants": "~16.0.2",
"expo-linking": "~6.3.1",
"expo-router": "~3.5.17",
"expo-status-bar": "~1.12.1",
+ "graphql": "^15.9.0",
+ "graphql-request": "^6.1.0",
+ "install": "^0.13.0",
"react": "18.2.0",
"react-dom": "18.2.0",
"react-native": "0.74.2",
@@ -2388,6 +2392,14 @@
"integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==",
"license": "MIT"
},
+ "node_modules/@expo/cli/node_modules/graphql": {
+ "version": "15.8.0",
+ "resolved": "https://registry.npmjs.org/graphql/-/graphql-15.8.0.tgz",
+ "integrity": "sha512-5gghUc24tP9HRznNpV2+FIoq3xKkj5dTQqf4v0CpdPbFVwFkWoxOM+o+2OC9ZSvjEMTjfmG9QT+gcvggTwW1zw==",
+ "engines": {
+ "node": ">= 10.x"
+ }
+ },
"node_modules/@expo/cli/node_modules/has-flag": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
@@ -6604,6 +6616,30 @@
"@sinonjs/commons": "^3.0.0"
}
},
+ "node_modules/@tanstack/query-core": {
+ "version": "5.49.1",
+ "resolved": "https://registry.npmjs.org/@tanstack/query-core/-/query-core-5.49.1.tgz",
+ "integrity": "sha512-JnC9ndmD1KKS01Rt/ovRUB1tmwO7zkyXAyIxN9mznuJrcNtOrkmOnQqdJF2ib9oHzc2VxHomnEG7xyfo54Npkw==",
+ "funding": {
+ "type": "github",
+ "url": "https://github.com/sponsors/tannerlinsley"
+ }
+ },
+ "node_modules/@tanstack/react-query": {
+ "version": "5.49.2",
+ "resolved": "https://registry.npmjs.org/@tanstack/react-query/-/react-query-5.49.2.tgz",
+ "integrity": "sha512-6rfwXDK9BvmHISbNFuGd+wY3P44lyW7lWiA9vIFGT/T0P9aHD1VkjTvcM4SDAIbAQ9ygEZZoLt7dlU1o3NjMVA==",
+ "dependencies": {
+ "@tanstack/query-core": "5.49.1"
+ },
+ "funding": {
+ "type": "github",
+ "url": "https://github.com/sponsors/tannerlinsley"
+ },
+ "peerDependencies": {
+ "react": "^18.0.0"
+ }
+ },
"node_modules/@types/cookie": {
"version": "0.6.0",
"resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.6.0.tgz",
@@ -6697,7 +6733,6 @@
"version": "0.3.0",
"resolved": "https://registry.npmjs.org/@urql/exchange-retry/-/exchange-retry-0.3.0.tgz",
"integrity": "sha512-hHqer2mcdVC0eYnVNbWyi28AlGOPb2vjH3lP3/Bc8Lc8BjhMsDwFMm7WhoP5C1+cfbr/QJ6Er3H/L08wznXxfg==",
- "license": "MIT",
"dependencies": {
"@urql/core": ">=2.3.1",
"wonka": "^4.0.14"
@@ -9617,14 +9652,25 @@
"license": "ISC"
},
"node_modules/graphql": {
- "version": "15.8.0",
- "resolved": "https://registry.npmjs.org/graphql/-/graphql-15.8.0.tgz",
- "integrity": "sha512-5gghUc24tP9HRznNpV2+FIoq3xKkj5dTQqf4v0CpdPbFVwFkWoxOM+o+2OC9ZSvjEMTjfmG9QT+gcvggTwW1zw==",
- "license": "MIT",
+ "version": "15.9.0",
+ "resolved": "https://registry.npmjs.org/graphql/-/graphql-15.9.0.tgz",
+ "integrity": "sha512-GCOQdvm7XxV1S4U4CGrsdlEN37245eC8P9zaYCMr6K1BG0IPGy5lUwmJsEOGyl1GD6HXjOtl2keCP9asRBwNvA==",
"engines": {
"node": ">= 10.x"
}
},
+ "node_modules/graphql-request": {
+ "version": "6.1.0",
+ "resolved": "https://registry.npmjs.org/graphql-request/-/graphql-request-6.1.0.tgz",
+ "integrity": "sha512-p+XPfS4q7aIpKVcgmnZKhMNqhltk20hfXtkaIkTfjjmiKMJ5xrt5c743cL03y/K7y1rg3WrIC49xGiEQ4mxdNw==",
+ "dependencies": {
+ "@graphql-typed-document-node/core": "^3.2.0",
+ "cross-fetch": "^3.1.5"
+ },
+ "peerDependencies": {
+ "graphql": "14 - 16"
+ }
+ },
"node_modules/graphql-tag": {
"version": "2.12.6",
"resolved": "https://registry.npmjs.org/graphql-tag/-/graphql-tag-2.12.6.tgz",
@@ -9948,6 +9994,14 @@
"fast-loops": "^1.1.3"
}
},
+ "node_modules/install": {
+ "version": "0.13.0",
+ "resolved": "https://registry.npmjs.org/install/-/install-0.13.0.tgz",
+ "integrity": "sha512-zDml/jzr2PKU9I8J/xyZBQn8rPCAY//UOYNmR01XwNwyfhEWObo2SWfSl1+0tm1u6PhxLwDnfsT/6jB7OUxqFA==",
+ "engines": {
+ "node": ">= 0.10"
+ }
+ },
"node_modules/internal-ip": {
"version": "4.3.0",
"resolved": "https://registry.npmjs.org/internal-ip/-/internal-ip-4.3.0.tgz",
diff --git a/package.json b/package.json
index ace2cdb..1a7ddcb 100644
--- a/package.json
+++ b/package.json
@@ -9,17 +9,21 @@
"web": "expo start --web"
},
"dependencies": {
+ "@tanstack/react-query": "^5.49.2",
"expo": "~51.0.17",
+ "expo-constants": "~16.0.2",
+ "expo-linking": "~6.3.1",
+ "expo-router": "~3.5.17",
"expo-status-bar": "~1.12.1",
+ "graphql": "^15.9.0",
+ "graphql-request": "^6.1.0",
+ "install": "^0.13.0",
"react": "18.2.0",
+ "react-dom": "18.2.0",
"react-native": "0.74.2",
- "expo-router": "~3.5.17",
- "react-native-screens": "3.31.1",
- "expo-linking": "~6.3.1",
- "expo-constants": "~16.0.2",
"react-native-safe-area-context": "4.10.1",
- "react-native-web": "~0.19.10",
- "react-dom": "18.2.0"
+ "react-native-screens": "3.31.1",
+ "react-native-web": "~0.19.10"
},
"devDependencies": {
"@babel/core": "^7.20.0"
diff --git a/src/app/[name].jsx b/src/app/[name].jsx
index 99f6164..5cb3703 100644
--- a/src/app/[name].jsx
+++ b/src/app/[name].jsx
@@ -1,19 +1,48 @@
-import { View, Text, ScrollView } from "react-native";
+import { View, Text, ScrollView, ActivityIndicator } from "react-native";
import { useLocalSearchParams, Stack } from "expo-router";
import exercises from "../../assets/data/exercises.json";
import { StyleSheet } from "react-native";
import { useState } from "react";
+import { gql } from "graphql-request";
+import { useQuery } from "@tanstack/react-query";
+import client from "../graphqlClient";
+
+
+const exerciseQuery = gql`
+ query exercises($name: String) {
+ exercises(name: $name) {
+ equipment
+ instructions
+ name
+ muscle
+ }
+}
+`;
+
export default function ExerciseDetailsScreen() {
- const params = useLocalSearchParams();
+
+ const { name } = useLocalSearchParams();
+
+ const {data, isLoading, error} = useQuery({
+ queryKey: ['exercises',name],
+ queryFn: () => client.request(exerciseQuery, { name }),
+ });
+
const [isExpandInstructions, setIsExpandInstructions] = useState(false);
- const exercise = exercises.find((item) => item.name === params.name);
- if (!exercise) {
- return Exercise not found;
+ if (isLoading){
+ return ;
+ }
+
+ if (error) {
+ return Failed to fetch data.
}
+ const exercise = data.exercises[0];
+
+
return (
diff --git a/src/app/_layout.jsx b/src/app/_layout.jsx
index 2d24b64..c16141d 100644
--- a/src/app/_layout.jsx
+++ b/src/app/_layout.jsx
@@ -1,9 +1,14 @@
import { Stack, Slot } from "expo-router";
+import { QueryClientProvider, QueryClient } from "@tanstack/react-query";
+
+const client = new QueryClient();
export default function RootLayout() {
- return (
-
-
-
- );
-}
\ No newline at end of file
+ return (
+
+
+
+
+
+ );
+}
diff --git a/src/app/index.js b/src/app/index.js
index 9919842..a3a10ee 100644
--- a/src/app/index.js
+++ b/src/app/index.js
@@ -1,19 +1,52 @@
import { StatusBar } from "expo-status-bar";
-import { StyleSheet, Text, View, FlatList } from "react-native";
+import {
+ StyleSheet,
+ Text,
+ View,
+ FlatList,
+ ActivityIndicator,
+} from "react-native";
import exercises from "../../assets/data/exercises.json";
import ExerciseListItem from "../components/ExerciseListItem";
+import { useQuery } from "@tanstack/react-query";
+import { gql } from "graphql-request";
+import client from "../graphqlClient";
+const exercisesQuery = gql`
+ query MyQuery($muscle: String, $name: String) {
+ exercises(name: $name, muscle: $muscle) {
+ muscle
+ name
+ equipment
+ }
+ }
+`;
-export default function App() {
+export default function ExercisesScreen() {
+
+ const { data, isLoading, error } = useQuery({
+ queryKey: ["exercises"],
+ queryFn: () => client.request( exercisesQuery ),
+ });
+
+ if (isLoading) {
+ return ;
+ }
+
+ if (error) {
+ console.log(error);
+ return Failed to fetch data.;
+ }
+
+ console.log(data);
return (
item.name + index}
- renderItem={({ item }) => }
-
+ data={data.exercises}
+ contentContainerStyle={{ gap: 5 }}
+ keyExtractor={(item, index) => item.name + index}
+ renderItem={({ item }) => }
/>
@@ -26,7 +59,5 @@ const styles = StyleSheet.create({
flex: 1,
justifyContent: "center",
padding: 10,
-
},
-
});
diff --git a/src/graphqlClient.js b/src/graphqlClient.js
new file mode 100644
index 0000000..27c2a0e
--- /dev/null
+++ b/src/graphqlClient.js
@@ -0,0 +1,14 @@
+import { GraphQLClient } from "graphql-request";
+
+const url =
+ "https://thataluna.us-east-a.ibm.stepzen.net/api/invisible-donkey/graphql";
+
+const apiKey = process.env.EXPO_PUBLIC_GRAPQL_API_KEY;
+
+const client = new GraphQLClient(url, {
+ headers: {
+ Authorization: `apikey ${apiKey}`,
+ },
+});
+
+export default client;