diff --git a/src/components/navBar/navBar.js b/src/components/navBar/navBar.js index 3dafd92..d078418 100644 --- a/src/components/navBar/navBar.js +++ b/src/components/navBar/navBar.js @@ -22,6 +22,7 @@ import viadeLogo from './../../assets/logo/logo_alt.jpeg'; import viadeText from './../../assets/logo/logo_letters.jpeg'; import RouteManager from "./../../model/RouteManager"; import ShareView from '../../pages/ShareView'; +import RouteSharedList from "../../pages/RouteSharedList"; const routeManager = RouteManager; @@ -63,6 +64,8 @@ function MyNavBar(props) { {t('navBarMyRoutes')} {t('navBarCreateRoute')} + {t('navBarSharedRoutes')} + {t('navBarRouteHelp')} @@ -87,6 +90,7 @@ function MyNavBar(props) { } /> } /> + } /> } /> } /> diff --git a/src/components/podService/podStoreHandler.js b/src/components/podService/podStoreHandler.js index 30b463d..a81fe06 100644 --- a/src/components/podService/podStoreHandler.js +++ b/src/components/podService/podStoreHandler.js @@ -14,6 +14,7 @@ export default class PodStorageHandler extends PodHandler{ */ constructor(currentSession) { super(currentSession); + this.sharedRoutesToAdd = []; } /** @@ -115,7 +116,6 @@ export default class PodStorageHandler extends PodHandler{ } async getRoutesSharedToMe(forEachRoute = () => {}){ - let result = []; await this._getSharedFolder(async function (file) { // Transform file to JSON let fileAsJSON = JSON.parse(file); @@ -125,17 +125,14 @@ export default class PodStorageHandler extends PodHandler{ sharedRoutes = sharedRoutes.map((j) => { return j["@id"]; }); for (let i = 0; i < sharedRoutes.length; i++){ let fileUrl = sharedRoutes[i]; - console.log(fileUrl); await this.getFile(fileUrl).then( function(content) { // Create routes from JSON let routeObject = new MyRoute(); routeObject.modifyFromJsonLd(JSON.parse(content)); forEachRoute(routeObject); - result.push(routeObject); - }, (error) => {} ); + }, (error) => {forEachRoute(null);} ); } }.bind(this)); - return result; } /** @@ -152,25 +149,21 @@ export default class PodStorageHandler extends PodHandler{ const parser = new N3.Parser(); parser.parse(content, function (error, quad, prefixes) { // parse the content of the message if (quad) { - if ( quad.predicate.id == "http://schema.org/text" ) { // If the quad is the url of the route + if ( quad.predicate.id === "http://schema.org/text" && quad.object.id.includes("/viade/routes/") ) { // If the quad is the url of the route forEachMail(quad.object.id); - console.log("PUSHED " + quad.object.id); - //newRoutes.push(quad.object.id); - this.addRoutesAsShared([quad.object.id.split("\"").join("")]); - this._markEmailAsRead(url); + this.sharedRoutesToAdd.push(quad.object.id.split("\"").join("")); } } }.bind(this)); - }.bind(this), - (error) => {} + }.bind(this), + (error) => {} ); }.bind(this)); - //await this.addRoutesAsShared(newRoutes); - }.bind(this), (error) => { } ); + this.addRoutesAsShared(this.sharedRoutesToAdd); } /** @@ -195,31 +188,44 @@ export default class PodStorageHandler extends PodHandler{ } async addRoutesAsShared(urls){ - console.log("HasBeenShared! " + urls); - - let content = JSON.stringify( - { - "@context": { - "@version": 1.1, - "routes": { - "@container": "@list", - "@id": "viade:routes" - }, - "viade": "http://arquisoft.github.io/viadeSpec/" - }, - "routes": urls.map((url) => {return {"@id": url.toString()}}) - }); + let file = null; + let filename = "en3a.json"; + + // 1.- Get a shared File + try { + file = await this.getFile(this.repository + this.defaultFolder + this.sharedDirectory + filename); + file = JSON.parse(file); + } catch (e) { + if (e.status !== 404) { + throw e; + } else { + file = { + "@context": { + "@version": 1.1, + "routes": { + "@container": "@list", + "@id": "viade:routes" + }, + "viade": "http://arquisoft.github.io/viadeSpec/" + }, + "routes": [] + }; + } + } - //console.log(urls); - //console.log(urls.map((url) => {return {"@id": url}})); - //console.log(content); + // 2.- Remove duplicated routes + let alreadyRoutes = file["routes"].map((url) => {return url["@id"];}); + urls.forEach((url) => { + if (alreadyRoutes.indexOf(url) === -1) { + alreadyRoutes.push( url ); + } + }); + urls = []; - let filename = Date.now() + ".json"; - this.storeFile(this.repository + this.defaultFolder + this.sharedDirectory + filename, content); - } + // 3.- Rewrite file + file["routes"] = alreadyRoutes.map((url) => {return {"@id": url.toString()}}); - _markEmailAsRead(url) { - //console.log("READ! " + url); + this.storeFile(this.repository + this.defaultFolder + this.sharedDirectory + filename, JSON.stringify(file)); } async getFolder(url) { diff --git a/src/components/routeList/RouteCard.js b/src/components/routeList/RouteCard.js index 67f76be..c670cb5 100644 --- a/src/components/routeList/RouteCard.js +++ b/src/components/routeList/RouteCard.js @@ -15,9 +15,24 @@ class RouteCard extends React.Component { style={{ borderRadius: "5px", margin: "0", height: "100%", width: "100%" }} /> }; + this.showShareButton = true; + if (props.showShareButton !== undefined) { + this.showShareButton = props.showShareButton; + } + + this.showInfoButton = true; + if (props.showInfoButton !== undefined) { + this.showInfoButton = props.showInfoButton; + } } render() { + + let buttons = [ + this.showInfoButton && , + this.showShareButton && + ]; + return ( @@ -28,8 +43,7 @@ class RouteCard extends React.Component { {this.route.name} {this.route.description} - - + {buttons} ); @@ -39,6 +53,9 @@ class RouteCard extends React.Component { this.setState({ mapComponent: this.state.mapComponent }); } + toggleShareButton(){ + this.showShareButton = !this.showShareButton; + } } diff --git a/src/i18n.js b/src/i18n.js index 6c905c9..4b8fa17 100644 --- a/src/i18n.js +++ b/src/i18n.js @@ -22,6 +22,7 @@ const resources = { "navBarRoutes": "Route management", "navBarMyRoutes": "My routes", "navBarCreateRoute": "Create a new route", + "navBarSharedRoutes" : "Shared to Me", "navBarRouteHelp": "How do routes work?", "routeListText": "Route List", "friendCardDelete": "Delete", @@ -107,6 +108,7 @@ const resources = { "navBarRoutes": "Gestión de rutas", "navBarMyRoutes": "Mis rutas", "navBarCreateRoute": "Crear una nueva ruta", + "navBarSharedRoutes" : "Compartidas conmigo", "navBarRouteHelp": "¿Cómo funcionan las rutas?", "routeListText": "Lista de rutas", "friendCardDelete": "Borrar", diff --git a/src/model/RouteManager.js b/src/model/RouteManager.js index 95ebc62..d15c66e 100644 --- a/src/model/RouteManager.js +++ b/src/model/RouteManager.js @@ -1,7 +1,7 @@ class RouteManager { constructor() { - this.routes = []; + this.resetRoutes(); } getRoutes() { @@ -16,8 +16,17 @@ class RouteManager { this.routes.push(route); } + addSharedRoute(route){ + this.routesSharedToMe.push(route); + } + + getSharedRouteById(id) { + return this.routesSharedToMe.find((route) => route.getId() === id); + } + resetRoutes() { this.routes = []; + this.routesSharedToMe = []; } } diff --git a/src/pages/Home.js b/src/pages/Home.js index 7d89c0a..8e6504a 100644 --- a/src/pages/Home.js +++ b/src/pages/Home.js @@ -37,19 +37,6 @@ class Home extends Component {

V 1.0

); - - // - // - } - - async getEmail(){ - await new PodStorageHandler(await auth.currentSession()).checkInbox((r) => {}); // console.log("Callback called:"); console.log(r); - } - - async getSharedToMe(){ - let routes = await new PodStorageHandler(await auth.currentSession()).getRoutesSharedToMe((r) => {console.log("Callback called:"); console.log(r);}); - console.log("Function finished"); - console.log(routes); } async printName() { diff --git a/src/pages/RouteList.js b/src/pages/RouteList.js index 9aa6015..3a204b5 100644 --- a/src/pages/RouteList.js +++ b/src/pages/RouteList.js @@ -9,6 +9,7 @@ import MyRoute from "../model/MyRoute"; import $ from "jquery"; import 'react-toastify/dist/ReactToastify.css'; +import RouteManager from "../model/RouteManager"; const auth = require('solid-auth-client'); @@ -16,17 +17,20 @@ class RouteList extends React.Component { constructor(props) { super(props); - this.routeManager = props.routeManager; + this.routeManager = RouteManager; this.cardDeckSize = 4; this.state = { routes: [], - spinnerHidden: false + sharedRoutes : [], + spinnerHidden: false, }; - this.syncRoutesWithPod().then(() => { - this.state.spinnerHidden = true; - }); - this.processedRoutes = 0; - this.retrievedRoutes = 0; + if (props.sync == undefined || props.sync == true) { + this.syncRoutesWithPod().then(() => { + this.state.spinnerHidden = true; + }); + this.processedRoutes = 0; + this.retrievedRoutes = 0; + } } render() { @@ -74,6 +78,8 @@ class RouteList extends React.Component { let session = await auth.currentSession(); if (session !== null && session !== undefined) { let storageHandler = new PodStorageHandler(session); + + // Handle my Routes storageHandler.getRoutes((routeJson, error) => { if (routeJson === null) { toast.error("We can't access your POD. Please, review its permissions"); @@ -106,6 +112,19 @@ class RouteList extends React.Component { } } ); + + // Handle Shared Routes + storageHandler.getRoutesSharedToMe( (route) => { + if (route === undefined || route == null) { + toast.error("We can't access your POD. Please, review its permissions"); + } else { + this.routeManager.addSharedRoute(route); + let tempList = this.state.sharedRoutes; + tempList.push(route); + this.setState({ sharedRoutes: tempList }); + $("#messageArea").empty(); + } + }); } } diff --git a/src/pages/RouteSharedList.js b/src/pages/RouteSharedList.js new file mode 100644 index 0000000..5854744 --- /dev/null +++ b/src/pages/RouteSharedList.js @@ -0,0 +1,64 @@ +import React from "react"; +import RouteManager from "../model/RouteManager"; +import {CardDeck, Spinner} from "react-bootstrap"; +import RouteCard from "../components/routeList/RouteCard"; +import {toast, ToastContainer} from "react-toastify"; +import {Translation} from "react-i18next"; +import PodStorageHandler from "../components/podService/podStoreHandler"; +import MyRoute from "../model/MyRoute"; +import $ from "jquery"; +import RouteList from "./RouteList"; +const auth = require('solid-auth-client'); + +export default class RouteSharedList extends RouteList { + + constructor(props) { + super(props); + if (props.sync === undefined || props.sync == true) + this.readInbox(); + } + + async readInbox() { + new PodStorageHandler(await auth.currentSession()).checkInbox(); + } + + render() { + let routesForCardDecks = []; + let counter = 0; + while (counter <= this.state.sharedRoutes.length) { + routesForCardDecks.push( + + {this.state.sharedRoutes.slice(counter, counter + this.cardDeckSize).map( + (r) => {return ;} + )} + + ); + counter += this.cardDeckSize; + } + + return ( +
+ + + { + (t) =>

{t('routeListText')}

+ } +
+ + { + (t) => + } + + +
+ ); + } +} \ No newline at end of file diff --git a/src/tests/RouteSharedList.test.js b/src/tests/RouteSharedList.test.js new file mode 100644 index 0000000..ac2b026 --- /dev/null +++ b/src/tests/RouteSharedList.test.js @@ -0,0 +1,24 @@ +import React from "react"; +import { render } from "@testing-library/react"; +import RouteManager from "./../model/RouteManager"; +import RouteList from "./../pages/RouteList"; +import MyRoute from "../model/MyRoute"; +import RouteSharedList from "../pages/RouteSharedList"; + +const routeManager = RouteManager; + +test("renders learn react link", () => { + const routeManager = RouteManager; + const myRoute = new MyRoute( + "Fuso de la Reina", + "María santísima", + "Easy to complete, mostly straight lines. Concrete does its job turning your knees into dust.", + [{ lat: 2, lng: 4 }, { lat: 24, lng: 13 }], + {} + ); + routeManager.addSharedRoute(myRoute); + + const { getByText } = render(); + const route1 = getByText('routeListText'); + expect(route1).toBeInTheDocument(); +}); \ No newline at end of file