{"version":3,"sources":["components/api-authorization/ApiAuthorizationConstants.js","components/api-authorization/AuthorizeService.js","exchanges/refreshTokenExchange.js","components/api-authorization/AuthorizeRoute.js","components/api-authorization/Login.js","components/api-authorization/Logout.js","components/api-authorization/ApiAuthorizationRoutes.js","components/api-authorization/LoginMenu.js","components/NavMenu.js","components/Layout.js","components/Home.js","components/PageTitle.js","components/Category.js","components/Marble.js","components/Masonary.js","hooks/useEventListener.js","routes/earn/EarnScreen.js","routes/earn/marble/EarnNewMarbleScreen.js","components/app/TitleBar.js","components/app/Dashboard.js","components/app/MenuBar.js","components/app/Footer.js","components/app/AuthorizedLayout.js","App.js","index.js"],"names":["QueryParameterNames","LogoutActions","LoginActions","authServerUrl","prefix","ApplicationPaths","DefaultLoginRedirectPath","ApiAuthorizationClientConfigurationUrl","ApiAuthorizationPrefix","Login","LoginFailed","LoginCallback","Register","Profile","LogOut","LoggedOut","LogOutCallback","IdentityRegisterPath","IdentityManagePath","clientConfiguration","authority","client_id","redirect_uri","post_logout_redirect_uri","response_type","scope","authService","_callbacks","_nextSubscriptionId","_user","_isAuthenticated","_popUpDisabled","this","getUser","user","profile","ensureUserManagerInitialized","userManager","access_token","state","signinSilent","createArguments","silentUser","updateState","success","console","log","Error","signinPopup","popUpUser","message","error","signinRedirect","redirect","url","signinCallback","signoutPopup","undefined","signoutRedirect","signoutCallback","response","data","notifySubscribers","callback","push","subscription","subscriptionId","subscriptionIndex","map","element","index","found","filter","length","splice","i","useReplaceToNavigate","status","AuthenticationResultStatus","Fail","Success","Redirect","settings","automaticSilentRenew","includeIdTokenInSilentRenew","userStore","WebStorageStateStore","UserManager","events","addUserSignedOut","a","removeUser","refreshTokenExchange","promise","forward","ops$","pipe","mergeMap","op","fromPromise","getAccessToken","newToken","fetchOptions","headers","authorization","origin","window","location","context","token","AuthorizeRoute","props","ready","authenticated","_subscription","subscribe","authenticationChanged","populateAuthenticationState","unsubscribe","redirectUrl","encodeURI","href","Component","component","rest","render","to","isAuthenticated","setState","action","login","getReturnUrl","processLoginCallback","URLSearchParams","search","get","redirectToProfile","redirectToRegister","returnUrl","signIn","result","navigateToReturnUrl","completeSignIn","fromQuery","startsWith","redirectToApiAuthorizationPath","apiAuthorizationPath","replace","Logout","isReady","history","local","logout","processLogoutCallback","signOut","completeSignOut","ApiAuthorizationRoutes","path","loginAction","logoutAction","name","LoginMenu","userName","populateState","Promise","all","profilePath","logoutPath","pathname","authenticatedView","registerPath","loginPath","anonymousView","NavItem","NavLink","tag","Link","className","NavMenu","toggleNavbar","bind","collapsed","Navbar","light","NavbarBrand","NavbarToggler","onClick","Collapse","isOpen","navbar","displayName","Layout","Container","children","Home","useState","setIsAuthenticated","useEffect","tempIsAuthenticated","f","PageTitleStyled","styled","div","PageTitle","value","LayoutStyled","CategoryStyled","Category","category","categoryName","TitleStyled","CircleStyled","LastUsedStyled","MainStyled","Marble","marble","id","marbleName","marbleStats","lastEarnedOn","Dropdown","Menu","Item","Divider","MasonryStyled","gap","ColStyled","fillCols","cols","forEach","child","Masonry","minWidth","ref","useRef","numCols","setNumCols","Array","resizeHandler","Math","ceil","current","offsetWidth","eventName","handler","savedHandler","addEventListener","eventListener","event","removeEventListener","useEventListener","_","key","fetchCategories","gql","EarnScreen","useHistory","useQuery","query","handleMarbleClick","marbleId","fetching","categories","marbles","earnMarbleMutation","EarnNewMarbleScreen","useParams","earnedOn","format","Date","marbleEarned","setMarbleEarned","useMutation","earnMarble","handleInputChange","target","type","checked","saveEarnMarble","userId","sub","marbleEarnedInput","lengthOfTime","parseInt","variables","Segment","Header","as","Form","Grid","Column","width","Field","Input","placeholder","onChange","inline","notes","Row","columns","Button","icon","content","textAlign","color","TitleBar","BoxStyled","delayedFadeIn","keyframes","plusOne","DayWrapperStyled","DayStyled","animate","PlusOneStyled","Dashboard","marbleStatistics","todayCount","todayJustAddedCount","setTodayJustAddedCount","LinkStyled","MenuBar","CopyrightStyled","Footer","AuthorizedLayout","baseUrl","document","getElementsByTagName","getAttribute","rootElement","getElementById","ReactDOM","basename","client","createClient","exchanges","cacheExchange","fetchExchange","exact"],"mappings":"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","file":"static/js/main.75fe120c.chunk.js","sourcesContent":["export const ApplicationName = 'FindMyMarblesWeb';\r\n\r\nexport const QueryParameterNames = {\r\n ReturnUrl: 'returnUrl',\r\n Message: 'message'\r\n};\r\n\r\nexport const LogoutActions = {\r\n LogoutCallback: 'logout-callback',\r\n Logout: 'logout',\r\n LoggedOut: 'logged-out'\r\n};\r\n\r\nexport const LoginActions = {\r\n Login: 'login',\r\n LoginCallback: 'login-callback',\r\n LoginFailed: 'login-failed',\r\n Profile: 'profile',\r\n Register: 'register'\r\n};\r\n\r\nconst thisServerUrl = process.env.NODE_ENV === 'development' ? 'https://brodiedev.com:5007' : 'https://www.findmymarbles.com'\r\nconst authServerUrl = process.env.NODE_ENV === 'development' ? 'https://brodiedev.com:5001' : 'https://auth.findmymarbles.com'; // TODO: move to config\r\n\r\nconst prefix = `/authentication`;\r\n\r\nexport const ApplicationPaths = {\r\n DefaultLoginRedirectPath: '/',\r\n ApiAuthorizationClientConfigurationUrl: `${authServerUrl}/_configuration/${ApplicationName}`,\r\n ApiAuthorizationPrefix: prefix,\r\n Login: `${prefix}/${LoginActions.Login}`,\r\n LoginFailed: `${prefix}/${LoginActions.LoginFailed}`,\r\n LoginCallback: `${prefix}/${LoginActions.LoginCallback}`,\r\n Register: `${prefix}/${LoginActions.Register}`,\r\n Profile: `${prefix}/${LoginActions.Profile}`,\r\n LogOut: `${prefix}/${LogoutActions.Logout}`,\r\n LoggedOut: `${prefix}/${LogoutActions.LoggedOut}`,\r\n LogOutCallback: `${prefix}/${LogoutActions.LogoutCallback}`,\r\n IdentityRegisterPath: `${authServerUrl}/auth/Identity/Account/Register`,\r\n IdentityManagePath: `${authServerUrl}/auth/Identity/Account/Manage`\r\n};\r\n\r\nexport const clientConfiguration = {\r\n authority: authServerUrl,\r\n client_id: \"FindMyMarblesWeb\",\r\n redirect_uri: `${thisServerUrl}/authentication/login-callback`,\r\n post_logout_redirect_uri: `${thisServerUrl}/authentication/logout-callback`,\r\n response_type: \"code\",\r\n scope: \"FindMyMarblesApi openid profile\"\r\n};\r\n","import { UserManager, WebStorageStateStore } from 'oidc-client';\r\nimport { ApplicationPaths, ApplicationName, clientConfiguration } from './ApiAuthorizationConstants';\r\n\r\nexport class AuthorizeService {\r\n _callbacks = [];\r\n _nextSubscriptionId = 0;\r\n _user = null;\r\n _isAuthenticated = false;\r\n\r\n // By default pop ups are disabled because they don't work properly on Edge.\r\n // If you want to enable pop up authentication simply set this flag to false.\r\n _popUpDisabled = true;\r\n\r\n async isAuthenticated() {\r\n const user = await this.getUser();\r\n return !!user;\r\n }\r\n\r\n async getUser() {\r\n if (this._user && this._user.profile) {\r\n return this._user.profile;\r\n }\r\n\r\n await this.ensureUserManagerInitialized();\r\n const user = await this.userManager.getUser();\r\n return user && user.profile;\r\n }\r\n\r\n getAccessTokenSync() {\r\n return this._user && this._user.access_token;\r\n }\r\n\r\n async getAccessToken() {\r\n await this.ensureUserManagerInitialized();\r\n const user = await this.userManager.getUser();\r\n return user && user.access_token;\r\n }\r\n\r\n // We try to authenticate the user in three different ways:\r\n // 1) We try to see if we can authenticate the user silently. This happens\r\n // when the user is already logged in on the IdP and is done using a hidden iframe\r\n // on the client.\r\n // 2) We try to authenticate the user using a PopUp Window. This might fail if there is a\r\n // Pop-Up blocker or the user has disabled PopUps.\r\n // 3) If the two methods above fail, we redirect the browser to the IdP to perform a traditional\r\n // redirect flow.\r\n async signIn(state) {\r\n await this.ensureUserManagerInitialized();\r\n try {\r\n const silentUser = await this.userManager.signinSilent(this.createArguments());\r\n this.updateState(silentUser);\r\n return this.success(state);\r\n } catch (silentError) {\r\n // User might not be authenticated, fallback to popup authentication\r\n console.log(\"Silent authentication error: \", silentError);\r\n\r\n try {\r\n if (this._popUpDisabled) {\r\n throw new Error('Popup disabled. Change \\'AuthorizeService.js:AuthorizeService._popupDisabled\\' to false to enable it.')\r\n }\r\n\r\n const popUpUser = await this.userManager.signinPopup(this.createArguments()); \r\n this.updateState(popUpUser);\r\n return this.success(state);\r\n } catch (popUpError) {\r\n if (popUpError.message === \"Popup window closed\") {\r\n // The user explicitly cancelled the login action by closing an opened popup.\r\n return this.error(\"The user closed the window.\");\r\n } else if (!this._popUpDisabled) {\r\n console.log(\"Popup authentication error: \", popUpError);\r\n }\r\n\r\n // PopUps might be blocked by the user, fallback to redirect\r\n try { \r\n await this.userManager.signinRedirect(this.createArguments(state));\r\n return this.redirect();\r\n } catch (redirectError) {\r\n console.log(\"Redirect authentication error: \", redirectError);\r\n return this.error(redirectError);\r\n }\r\n }\r\n }\r\n }\r\n\r\n async completeSignIn(url) {\r\n try {\r\n await this.ensureUserManagerInitialized();\r\n const user = await this.userManager.signinCallback(url);\r\n this.updateState(user);\r\n return this.success(user && user.state);\r\n } catch (error) {\r\n console.log('There was an error signing in: ', error);\r\n return this.error('There was an error signing in.');\r\n }\r\n }\r\n\r\n // We try to sign out the user in two different ways:\r\n // 1) We try to do a sign-out using a PopUp Window. This might fail if there is a\r\n // Pop-Up blocker or the user has disabled PopUps.\r\n // 2) If the method above fails, we redirect the browser to the IdP to perform a traditional\r\n // post logout redirect flow.\r\n async signOut(state) {\r\n await this.ensureUserManagerInitialized();\r\n try {\r\n if (this._popUpDisabled) {\r\n throw new Error('Popup disabled. Change \\'AuthorizeService.js:AuthorizeService._popupDisabled\\' to false to enable it.')\r\n }\r\n\r\n await this.userManager.signoutPopup(this.createArguments());\r\n this.updateState(undefined);\r\n return this.success(state);\r\n } catch (popupSignOutError) {\r\n console.log(\"Popup signout error: \", popupSignOutError);\r\n try {\r\n await this.userManager.signoutRedirect(this.createArguments(state));\r\n return this.redirect();\r\n } catch (redirectSignOutError) {\r\n console.log(\"Redirect signout error: \", redirectSignOutError);\r\n return this.error(redirectSignOutError);\r\n }\r\n }\r\n }\r\n\r\n async completeSignOut(url) {\r\n await this.ensureUserManagerInitialized();\r\n try {\r\n const response = await this.userManager.signoutCallback(url);\r\n this.updateState(null);\r\n return this.success(response && response.data);\r\n } catch (error) {\r\n console.log(`There was an error trying to log out '${error}'.`);\r\n return this.error(error);\r\n }\r\n }\r\n\r\n updateState(user) {\r\n this._user = user;\r\n this._isAuthenticated = !!this._user;\r\n this.notifySubscribers();\r\n }\r\n\r\n subscribe(callback) {\r\n this._callbacks.push({ callback, subscription: this._nextSubscriptionId++ });\r\n return this._nextSubscriptionId - 1;\r\n }\r\n\r\n unsubscribe(subscriptionId) {\r\n const subscriptionIndex = this._callbacks\r\n .map((element, index) => element.subscription === subscriptionId ? { found: true, index } : { found: false })\r\n .filter(element => element.found === true);\r\n if (subscriptionIndex.length !== 1) {\r\n throw new Error(`Found an invalid number of subscriptions ${subscriptionIndex.length}`);\r\n }\r\n\r\n this._callbacks = this._callbacks.splice(subscriptionIndex[0].index, 1);\r\n }\r\n\r\n notifySubscribers() {\r\n for (let i = 0; i < this._callbacks.length; i++) {\r\n const callback = this._callbacks[i].callback;\r\n callback();\r\n }\r\n }\r\n\r\n createArguments(state) {\r\n return { useReplaceToNavigate: true, data: state };\r\n }\r\n\r\n error(message) {\r\n return { status: AuthenticationResultStatus.Fail, message };\r\n }\r\n\r\n success(state) {\r\n return { status: AuthenticationResultStatus.Success, state };\r\n }\r\n\r\n redirect() {\r\n return { status: AuthenticationResultStatus.Redirect };\r\n }\r\n\r\n async ensureUserManagerInitialized() {\r\n if (this.userManager !== undefined) {\r\n return;\r\n }\r\n \r\n let settings = clientConfiguration;\r\n settings.automaticSilentRenew = true;\r\n settings.includeIdTokenInSilentRenew = true;\r\n settings.userStore = new WebStorageStateStore({\r\n prefix: ApplicationName\r\n });\r\n\r\n this.userManager = new UserManager(settings);\r\n\r\n this.userManager.events.addUserSignedOut(async () => {\r\n await this.userManager.removeUser();\r\n this.updateState(undefined);\r\n });\r\n }\r\n\r\n static get instance() { return authService }\r\n}\r\n\r\nconst authService = new AuthorizeService();\r\n\r\nexport default authService;\r\n\r\nexport const AuthenticationResultStatus = {\r\n Redirect: 'redirect',\r\n Success: 'success',\r\n Fail: 'fail'\r\n};\r\n","import { mergeMap, pipe, fromPromise, map, fromValue } from \"wonka\";\r\nimport authService from '../components/api-authorization/AuthorizeService'\r\n\r\nexport const refreshTokenExchange = () => {\r\n let promise;\r\n return ({ forward }) => ops$ =>\r\n pipe(\r\n ops$,\r\n mergeMap(op => {\r\n return pipe(\r\n fromPromise(promise ? promise : (promise = authService.getAccessToken())),\r\n map(newToken => {\r\n promise = undefined; \r\n const fetchOptions = { \r\n headers: { \r\n authorization: `Bearer ${newToken}`,\r\n origin: window.location.origin\r\n }\r\n };\r\n return { ...op, context: { ...op.context, token: newToken, fetchOptions } };\r\n })\r\n ); \r\n }),\r\n forward\r\n );\r\n};","import React from 'react'\r\nimport { Component } from 'react'\r\nimport { Route, Redirect } from 'react-router-dom'\r\nimport { ApplicationPaths, QueryParameterNames } from './ApiAuthorizationConstants'\r\nimport authService from './AuthorizeService'\r\n\r\nexport default class AuthorizeRoute extends Component {\r\n constructor(props) {\r\n super(props);\r\n\r\n this.state = {\r\n ready: false,\r\n authenticated: false\r\n };\r\n }\r\n\r\n componentDidMount() {\r\n this._subscription = authService.subscribe(() => this.authenticationChanged());\r\n this.populateAuthenticationState();\r\n }\r\n\r\n componentWillUnmount() {\r\n authService.unsubscribe(this._subscription);\r\n }\r\n\r\n render() {\r\n const { ready, authenticated } = this.state;\r\n const redirectUrl = `${ApplicationPaths.Login}?${QueryParameterNames.ReturnUrl}=${encodeURI(window.location.href)}`\r\n if (!ready) {\r\n return
;\r\n } else {\r\n const { component: Component, ...rest } = this.props;\r\n return {\r\n if (authenticated) {\r\n return \r\n } else {\r\n return \r\n }\r\n }} />\r\n }\r\n }\r\n\r\n async populateAuthenticationState() {\r\n const authenticated = await authService.isAuthenticated();\r\n this.setState({ ready: true, authenticated });\r\n }\r\n\r\n async authenticationChanged() {\r\n this.setState({ ready: false, authenticated: false });\r\n await this.populateAuthenticationState();\r\n }\r\n}\r\n","import React from 'react'\r\nimport { Component } from 'react';\r\nimport authService from './AuthorizeService';\r\nimport { AuthenticationResultStatus } from './AuthorizeService';\r\nimport { LoginActions, QueryParameterNames, ApplicationPaths } from './ApiAuthorizationConstants';\r\n\r\n// The main responsibility of this component is to handle the user's login process.\r\n// This is the starting point for the login process. Any component that needs to authenticate\r\n// a user can simply perform a redirect to this component with a returnUrl query parameter and\r\n// let the component perform the login and return back to the return url.\r\nexport class Login extends Component {\r\n constructor(props) {\r\n super(props);\r\n\r\n this.state = {\r\n message: undefined\r\n };\r\n }\r\n\r\n componentDidMount() {\r\n const action = this.props.action;\r\n switch (action) {\r\n case LoginActions.Login:\r\n this.login(this.getReturnUrl());\r\n break;\r\n case LoginActions.LoginCallback:\r\n this.processLoginCallback();\r\n break;\r\n case LoginActions.LoginFailed:\r\n const params = new URLSearchParams(window.location.search);\r\n const error = params.get(QueryParameterNames.Message);\r\n this.setState({ message: error });\r\n break;\r\n case LoginActions.Profile:\r\n this.redirectToProfile();\r\n break;\r\n case LoginActions.Register:\r\n this.redirectToRegister();\r\n break;\r\n default:\r\n throw new Error(`Invalid action '${action}'`);\r\n }\r\n }\r\n\r\n render() {\r\n const action = this.props.action;\r\n const { message } = this.state;\r\n\r\n if (!!message) {\r\n return
{message}
\r\n } else {\r\n switch (action) {\r\n case LoginActions.Login:\r\n return (
Processing login
);\r\n case LoginActions.LoginCallback:\r\n return (
Processing login callback
);\r\n case LoginActions.Profile:\r\n case LoginActions.Register:\r\n return (
);\r\n default:\r\n throw new Error(`Invalid action '${action}'`);\r\n }\r\n }\r\n }\r\n\r\n async login(returnUrl) {\r\n const state = { returnUrl };\r\n const result = await authService.signIn(state);\r\n switch (result.status) {\r\n case AuthenticationResultStatus.Redirect:\r\n break;\r\n case AuthenticationResultStatus.Success:\r\n await this.navigateToReturnUrl(returnUrl);\r\n break;\r\n case AuthenticationResultStatus.Fail: \r\n this.setState({ message: result.message });\r\n break;\r\n default:\r\n throw new Error(`Invalid status result ${result.status}.`);\r\n }\r\n }\r\n\r\n async processLoginCallback() {\r\n const url = window.location.href;\r\n const result = await authService.completeSignIn(url);\r\n switch (result.status) {\r\n case AuthenticationResultStatus.Redirect:\r\n // There should not be any redirects as the only time completeSignIn finishes\r\n // is when we are doing a redirect sign in flow.\r\n throw new Error('Should not redirect.');\r\n case AuthenticationResultStatus.Success:\r\n await this.navigateToReturnUrl(this.getReturnUrl(result.state));\r\n break;\r\n case AuthenticationResultStatus.Fail:\r\n this.setState({ message: result.message });\r\n break;\r\n default:\r\n throw new Error(`Invalid authentication result status '${result.status}'.`);\r\n }\r\n }\r\n\r\n getReturnUrl(state) {\r\n const params = new URLSearchParams(window.location.search);\r\n const fromQuery = params.get(QueryParameterNames.ReturnUrl);\r\n if (fromQuery && !fromQuery.startsWith(`${window.location.origin}/`)) {\r\n // This is an extra check to prevent open redirects.\r\n throw new Error(\"Invalid return url. The return url needs to have the same origin as the current page.\")\r\n }\r\n return (state && state.returnUrl) || fromQuery || `${window.location.origin}/`;\r\n }\r\n\r\n redirectToRegister() {\r\n this.redirectToApiAuthorizationPath(`${ApplicationPaths.IdentityRegisterPath}?${QueryParameterNames.ReturnUrl}=${encodeURI(ApplicationPaths.Login)}`);\r\n }\r\n\r\n redirectToProfile() {\r\n this.redirectToApiAuthorizationPath(ApplicationPaths.IdentityManagePath);\r\n }\r\n\r\n redirectToApiAuthorizationPath(apiAuthorizationPath) {\r\n const redirectUrl = `${window.location.origin}${apiAuthorizationPath}`;\r\n // It's important that we do a replace here so that when the user hits the back arrow on the\r\n // browser he gets sent back to where it was on the app instead of to an endpoint on this\r\n // component.\r\n window.location.replace(redirectUrl);\r\n }\r\n\r\n navigateToReturnUrl(returnUrl) {\r\n // It's important that we do a replace here so that we remove the callback uri with the\r\n // fragment containing the tokens from the browser history.\r\n window.location.replace(returnUrl);\r\n }\r\n}\r\n","import React from 'react'\r\nimport { Component } from 'react';\r\nimport authService from './AuthorizeService';\r\nimport { AuthenticationResultStatus } from './AuthorizeService';\r\nimport { QueryParameterNames, LogoutActions, ApplicationPaths } from './ApiAuthorizationConstants';\r\n\r\n// The main responsibility of this component is to handle the user's logout process.\r\n// This is the starting point for the logout process, which is usually initiated when a\r\n// user clicks on the logout button on the LoginMenu component.\r\nexport class Logout extends Component {\r\n constructor(props) {\r\n super(props);\r\n\r\n this.state = {\r\n message: undefined,\r\n isReady: false,\r\n authenticated: false\r\n };\r\n }\r\n\r\n componentDidMount() {\r\n const action = this.props.action;\r\n switch (action) {\r\n case LogoutActions.Logout:\r\n if (!!window.history.state.state.local) {\r\n this.logout(this.getReturnUrl());\r\n } else {\r\n // This prevents regular links to /authentication/logout from triggering a logout\r\n this.setState({ isReady: true, message: \"The logout was not initiated from within the page.\" });\r\n }\r\n break;\r\n case LogoutActions.LogoutCallback:\r\n this.processLogoutCallback();\r\n break;\r\n case LogoutActions.LoggedOut:\r\n this.setState({ isReady: true, message: \"You successfully logged out!\" });\r\n break;\r\n default:\r\n throw new Error(`Invalid action '${action}'`);\r\n }\r\n\r\n this.populateAuthenticationState();\r\n }\r\n\r\n render() {\r\n const { isReady, message } = this.state;\r\n if (!isReady) {\r\n return
\r\n }\r\n if (!!message) {\r\n return (
{message}
);\r\n } else {\r\n const action = this.props.action;\r\n switch (action) {\r\n case LogoutActions.Logout:\r\n return (
Processing logout
);\r\n case LogoutActions.LogoutCallback:\r\n return (
Processing logout callback
);\r\n case LogoutActions.LoggedOut:\r\n return (
{message}
);\r\n default:\r\n throw new Error(`Invalid action '${action}'`);\r\n }\r\n }\r\n }\r\n\r\n async logout(returnUrl) {\r\n const state = { returnUrl };\r\n const isauthenticated = await authService.isAuthenticated();\r\n if (isauthenticated) {\r\n const result = await authService.signOut(state);\r\n switch (result.status) {\r\n case AuthenticationResultStatus.Redirect:\r\n break;\r\n case AuthenticationResultStatus.Success:\r\n await this.navigateToReturnUrl(returnUrl);\r\n break;\r\n case AuthenticationResultStatus.Fail:\r\n this.setState({ message: result.message });\r\n break;\r\n default:\r\n throw new Error(\"Invalid authentication result status.\");\r\n }\r\n } else {\r\n this.setState({ message: \"You successfully logged out!\" });\r\n }\r\n }\r\n\r\n async processLogoutCallback() {\r\n const url = window.location.href;\r\n const result = await authService.completeSignOut(url);\r\n switch (result.status) {\r\n case AuthenticationResultStatus.Redirect:\r\n // There should not be any redirects as the only time completeAuthentication finishes\r\n // is when we are doing a redirect sign in flow.\r\n throw new Error('Should not redirect.');\r\n case AuthenticationResultStatus.Success:\r\n await this.navigateToReturnUrl(this.getReturnUrl(result.state));\r\n break;\r\n case AuthenticationResultStatus.Fail:\r\n this.setState({ message: result.message });\r\n break;\r\n default:\r\n throw new Error(\"Invalid authentication result status.\");\r\n }\r\n }\r\n\r\n async populateAuthenticationState() {\r\n const authenticated = await authService.isAuthenticated();\r\n this.setState({ isReady: true, authenticated });\r\n }\r\n\r\n getReturnUrl(state) {\r\n const params = new URLSearchParams(window.location.search);\r\n const fromQuery = params.get(QueryParameterNames.ReturnUrl);\r\n if (fromQuery && !fromQuery.startsWith(`${window.location.origin}/`)) {\r\n // This is an extra check to prevent open redirects.\r\n throw new Error(\"Invalid return url. The return url needs to have the same origin as the current page.\")\r\n }\r\n return (state && state.returnUrl) ||\r\n fromQuery ||\r\n `${window.location.origin}${ApplicationPaths.LoggedOut}`;\r\n }\r\n\r\n navigateToReturnUrl(returnUrl) {\r\n return window.location.replace(returnUrl);\r\n }\r\n}\r\n","import React, { Component, Fragment } from 'react';\r\nimport { Route } from 'react-router';\r\nimport { Login } from './Login'\r\nimport { Logout } from './Logout'\r\nimport { ApplicationPaths, LoginActions, LogoutActions } from './ApiAuthorizationConstants';\r\n\r\nexport default class ApiAuthorizationRoutes extends Component {\r\n\r\n render () {\r\n return(\r\n \r\n loginAction(LoginActions.Login)} />\r\n loginAction(LoginActions.LoginFailed)} />\r\n loginAction(LoginActions.LoginCallback)} />\r\n loginAction(LoginActions.Profile)} />\r\n loginAction(LoginActions.Register)} />\r\n logoutAction(LogoutActions.Logout)} />\r\n logoutAction(LogoutActions.LogoutCallback)} />\r\n logoutAction(LogoutActions.LoggedOut)} />\r\n );\r\n }\r\n}\r\n\r\nfunction loginAction(name){\r\n return ();\r\n}\r\n\r\nfunction logoutAction(name) {\r\n return ();\r\n}\r\n","import React, { Component, Fragment } from 'react';\r\nimport { NavItem, NavLink } from 'reactstrap';\r\nimport { Link } from 'react-router-dom';\r\nimport authService from './AuthorizeService';\r\nimport { ApplicationPaths } from './ApiAuthorizationConstants';\r\n\r\nexport class LoginMenu extends Component {\r\n constructor(props) {\r\n super(props);\r\n\r\n this.state = {\r\n isAuthenticated: false,\r\n userName: null\r\n };\r\n }\r\n\r\n componentDidMount() {\r\n this._subscription = authService.subscribe(() => this.populateState());\r\n this.populateState();\r\n }\r\n\r\n componentWillUnmount() {\r\n authService.unsubscribe(this._subscription);\r\n }\r\n\r\n async populateState() {\r\n const [isAuthenticated, user] = await Promise.all([authService.isAuthenticated(), authService.getUser()])\r\n this.setState({\r\n isAuthenticated,\r\n userName: user && user.name\r\n });\r\n }\r\n\r\n render() {\r\n const { isAuthenticated, userName } = this.state;\r\n if (!isAuthenticated) {\r\n const registerPath = `${ApplicationPaths.Register}`;\r\n const loginPath = `${ApplicationPaths.Login}`;\r\n return this.anonymousView(registerPath, loginPath);\r\n } else {\r\n const profilePath = `${ApplicationPaths.Profile}`;\r\n const logoutPath = { pathname: `${ApplicationPaths.LogOut}`, state: { local: true } };\r\n return this.authenticatedView(userName, profilePath, logoutPath);\r\n }\r\n }\r\n\r\n authenticatedView(userName, profilePath, logoutPath) {\r\n return (\r\n \r\n Hello {userName}\r\n \r\n \r\n Logout\r\n \r\n );\r\n\r\n }\r\n\r\n anonymousView(registerPath, loginPath) {\r\n return (\r\n {/*\r\n Register\r\n */}\r\n \r\n Login\r\n \r\n );\r\n }\r\n}\r\n","import React, { Component } from 'react';\r\nimport { Collapse, Container, Navbar, NavbarBrand, NavbarToggler, NavItem, NavLink } from 'reactstrap';\r\nimport { Link } from 'react-router-dom';\r\nimport { LoginMenu } from './api-authorization/LoginMenu';\r\nimport './NavMenu.css';\r\n\r\nexport class NavMenu extends Component {\r\n static displayName = NavMenu.name;\r\n\r\n constructor (props) {\r\n super(props);\r\n\r\n this.toggleNavbar = this.toggleNavbar.bind(this);\r\n this.state = {\r\n collapsed: true\r\n };\r\n }\r\n\r\n toggleNavbar () {\r\n this.setState({\r\n collapsed: !this.state.collapsed\r\n });\r\n }\r\n\r\n render () {\r\n return (\r\n
\r\n \r\n \r\n FindMyMarbles.com\r\n \r\n \r\n
    \r\n \r\n Home\r\n \r\n \r\n \r\n
\r\n
\r\n
\r\n
\r\n
\r\n );\r\n }\r\n}\r\n","import React, { Component } from 'react';\r\nimport { Container } from 'semantic-ui-react';\r\nimport { NavMenu } from './NavMenu';\r\n\r\nexport class Layout extends Component {\r\n static displayName = Layout.name;\r\n\r\n render () {\r\n return (\r\n
\r\n \r\n \r\n {this.props.children}\r\n \r\n
\r\n );\r\n }\r\n}\r\n","import React, { useState, useEffect } from 'react'\r\nimport authService from './api-authorization/AuthorizeService'\r\n\r\nimport { Layout } from './Layout';\r\n\r\nexport default function Home() {\r\n const [isAuthenticated, setIsAuthenticated] = useState(false)\r\n\r\n useEffect(() => {\r\n let f = async () => {\r\n const tempIsAuthenticated = await authService.isAuthenticated()\r\n setIsAuthenticated(tempIsAuthenticated)\r\n }\r\n f()\r\n }, []\r\n )\r\n\r\n return (\r\n
\r\n

FindMyMarbles.com

\r\n\r\n

Currently under development.

\r\n {/*\r\n \r\n

Life is better when you fill it with constructive activities. Stop losing your marbles by losing sight of your goals.

\r\n\r\n

Track the stuff that is important to you and challenge yourself to keep going! \r\n FindMyMarbles.com is an app that makes this a breeze in 3 easy steps. \r\n Create a challenge, earn some marbles, and track your progress with interactive dashboards.\r\n Add as little or as much information as your want. The key is to keep earning marbles!\r\n Available on the web, Android or iPhone.

\r\n\r\n

1. Challenge yourself

\r\n \r\n

Are there things you want to do but have a hard time staying on track?\r\n We got you covered. Creating a challenge is a simple and a highly effective motivator. \r\n Pick the marble you want and how often you aim to earn it. \r\n

\r\n\r\n

Get updates on your challenges via email, push notifications, or text messages.

\r\n\r\n

screenshot

\r\n\r\n

2. Earn marbles

\r\n\r\n

Did something marble worthy? Time to earn son! \r\n Search for the marble you earned and fill out as little or as much detail as you want.\r\n Could be as simple as the \"Taking a break\" marble or as detailed as a full workout\r\n where you want to track all the details.\r\n

\r\n\r\n

screenshot

\r\n\r\n

3. Track progress

\r\n \r\n

We break down your progress by day, week, month, and year. Every screen you will see your totals.\r\n Drill down to see the breakdown with charts, trends, and history. \r\n

\r\n\r\n

screenshot

\r\n\r\n

...but wait there's more!

\r\n\r\n

Community

\r\n\r\n

\r\n Join a community focused on positivity! Praise others for their accomplishments and receive recognition for yours.\r\n FindMyMarbles.com has a new take on social that removes the noise and just allows the gooey goodness. Fill your social feed\r\n with others that are full of life just like you. We don't all have our marbles found yet but let's motivate each other\r\n to find them.\r\n

\r\n\r\n

screenshot

\r\n \r\n

Leaderboard

\r\n\r\n

Compete against your friends and the large marble community. Do you have what it takes to be in the top ten?

\r\n\r\n

New challenges start every day.

\r\n\r\n

screenshot

\r\n\r\n

Sync smart devices

\r\n\r\n

Bring your data into FindMyMarbles.com for supported hardware.

\r\n\r\n

screenshot

\r\n\r\n

Do

\r\n\r\n

!greencheckmark Track the stuff that is important to you!

\r\n\r\n

Don't

\r\n\r\n

!redX Track stuff that is assigned to you.

*/}\r\n\r\n\r\n { isAuthenticated &&\r\n \r\n }\r\n\r\n
\r\n )\r\n}\r\n","import React from 'react';\r\nimport styled from 'styled-components';\r\n\r\nconst PageTitleStyled = styled.div`\r\n font-size: 2rem;\r\n font-weight: 700;\r\n color: hsla(208, 80%, 30%, 1);\r\n`;\r\n\r\nexport default function PageTitle({value}) {\r\n return {value}\r\n}","import React from 'react';\r\nimport styled from 'styled-components';\r\n\r\nconst LayoutStyled = styled.div`\r\n padding: 0rem;\r\n`;\r\nconst CategoryStyled = styled.div`\r\n font-size: 1.3rem;\r\n font-weight: 300;\r\n color: hsla(208, 18%, 56%, 1);\r\n`;\r\n\r\nexport default function Category({category, children}) {\r\n return (\r\n \r\n\t\t\t\t{category.categoryName}\r\n {children}\r\n\t\t\t\r\n )\r\n}\r\n","import React from 'react';\r\nimport styled from 'styled-components';\r\nimport { Dropdown } from 'semantic-ui-react'\r\n\r\nconst LayoutStyled = styled.div`\r\n display: flex;\r\n align-items: center;\r\n border: 1px solid hsla(208, 95%, 95%, 1);\r\n box-shadow: 0 1px 2px hsla(208, 95%, 95%, 0.20);\r\n border-radius: 12px;\r\n margin-top: .5rem;\r\n padding: .5rem;\r\n background-color: hsla(208, 100%, 100%, 1);\r\n`;\r\nconst TitleStyled = styled.div`\r\n font-size: 1rem;\r\n font-weight: 500;\r\n color: hsla(208, 80%, 30%, 1);\r\n`;\r\n\r\nconst CircleStyled = styled.div`\r\n background: hsla(208, 100%, 50%, 1);\r\n border: 1.5px solid #0F1C3F;\r\n border-radius: 50%;\r\n box-shadow: 2px 2px 0 0 rgba(15, 28, 63, 0.125);\r\n height: 2em;\r\n width: 2em;\r\n`\r\n\r\nconst LastUsedStyled = styled.div`\r\n font-size: 0.6rem;\r\n font-weight: 500;\r\n color: hsla(208, 80%, 30%, 1);\r\n`\r\n\r\nconst MainStyled = styled.div`\r\n flex: 1 1 auto;\r\n padding-left: 0.5rem;\r\n`\r\n\r\nexport default function Marble({marble, onClick}) {\r\n return (\r\n \r\n \r\n onClick(marble.id)}>\r\n {marble.marbleName}\r\n { marble.marbleStats &&\r\n Last used {marble.marbleStats.lastEarnedOn}\r\n }\r\n \r\n
\r\n \r\n \r\n Hide this marble\r\n \r\n Show history\r\n \r\n \r\n
\r\n\r\n\t\t\t
\r\n )\r\n}\r\n","import React, { useEffect, useRef, useState } from 'react'\r\nimport { useEventListener } from '../hooks/useEventListener'\r\nimport styled from 'styled-components'\r\n\r\nconst MasonryStyled = styled.div`\r\n display: grid;\r\n grid-auto-flow: column;\r\n grid-gap: ${props => props.gap || `1em`};\r\n`\r\n\r\nconst ColStyled = styled.div`\r\n display: grid;\r\n grid-gap: ${props => props.gap || `1em`};\r\n`\r\n\r\nconst fillCols = (children, cols) => {\r\n children.forEach((child, i) => cols[i % cols.length].push(child))\r\n}\r\n\r\nexport default function Masonry({ children, gap, minWidth = 500, ...rest }) {\r\n const ref = useRef()\r\n const [numCols, setNumCols] = useState(3)\r\n const cols = [...Array(numCols)].map(() => [])\r\n \r\n fillCols(children, cols)\r\n\r\n const resizeHandler = () =>\r\n setNumCols(Math.ceil(ref.current.offsetWidth / minWidth))\r\n useEffect(resizeHandler, [])\r\n useEventListener(`resize`, resizeHandler)\r\n\r\n return (\r\n \r\n {[...Array(numCols)].map((_, index) => (\r\n \r\n {cols[index]}\r\n \r\n ))}\r\n \r\n )\r\n}","import { useState, useRef, useEffect, useCallback } from 'react';\r\n\r\n// Hook\r\nexport function useEventListener(eventName, handler, element = window){\r\n // Create a ref that stores handler\r\n const savedHandler = useRef();\r\n \r\n // Update ref.current value if handler changes.\r\n // This allows our effect below to always get latest handler ...\r\n // ... without us needing to pass it in effect deps array ...\r\n // ... and potentially cause effect to re-run every render.\r\n useEffect(() => {\r\n savedHandler.current = handler;\r\n }, [handler]);\r\n\r\n useEffect(\r\n () => {\r\n // Make sure element supports addEventListener\r\n // On \r\n const isSupported = element && element.addEventListener;\r\n if (!isSupported) return;\r\n \r\n // Create event listener that calls handler function stored in ref\r\n const eventListener = event => savedHandler.current(event);\r\n \r\n // Add event listener\r\n element.addEventListener(eventName, eventListener);\r\n \r\n // Remove event listener on cleanup\r\n return () => {\r\n element.removeEventListener(eventName, eventListener);\r\n };\r\n },\r\n [eventName, element] // Re-run if eventName or element changes\r\n );\r\n};","import React from 'react'\r\nimport { useHistory } from 'react-router-dom'\r\nimport { useQuery } from 'urql'\r\nimport gql from 'graphql-tag'\r\nimport { Container } from 'semantic-ui-react'\r\n\r\nimport PageTitle from '../../components/PageTitle'\r\nimport Category from '../../components/Category'\r\nimport Marble from '../../components/Marble'\r\nimport Masonary from '../../components/Masonary'\r\n\r\nconst fetchCategories = gql`{\r\n categories {\r\n categoryName\r\n marbles {\r\n id\r\n marbleName\r\n picUrl\r\n createdByCurrentUser\r\n marbleStats {\r\n lastEarnedOn\r\n totalEarned\r\n }\r\n }\r\n }\r\n}`\r\n\r\nexport default function EarnScreen() {\r\n const history = useHistory();\r\n const [result] = useQuery({\r\n query: fetchCategories,\r\n });\r\n \r\n const handleMarbleClick = (marbleId) => {\r\n history.push(`/earn/marble/${marbleId}`);\r\n }\r\n\r\n if (result.error) return
Error: {result.error.message}
;\r\n if (result.fetching) return
Loading...
;\r\n \r\n return (\r\n \r\n\r\n \r\n\r\n \r\n { result.data.categories\r\n .filter(category => category.marbles.length > 0)\r\n .map(category =>\r\n \r\n \r\n {category.marbles && category.marbles.map(marble =>\r\n \r\n )}\r\n \r\n \r\n )}\r\n \r\n\r\n Don't see the marble you need? Create a new marble!\r\n\r\n \r\n )\r\n}","import React, { useState } from 'react'\r\nimport { useParams, useHistory } from 'react-router-dom'\r\nimport { useMutation } from 'urql'\r\nimport gql from 'graphql-tag'\r\nimport authService from '../../../components/api-authorization/AuthorizeService'\r\nimport {\r\n\tSegment,\r\n\tHeader,\r\n\tForm,\r\n\tGrid,\r\n\tInput,\r\n\tButton,\r\n\tDivider\r\n} from 'semantic-ui-react'\r\nimport { format } from 'date-fns'\r\n\r\nconst earnMarbleMutation = gql`\r\n mutation EarnMarble($marbleEarnedInput: MarbleEarnedInput!) {\r\n \tearnMarble(marbleEarned: $marbleEarnedInput) {\r\n\t\t\tid\r\n\t\t}\r\n\t}\r\n`;\r\n\r\nexport default function EarnNewMarbleScreen() {\r\n\tconst { marbleId } = useParams();\r\n\tconst history = useHistory()\r\n\tconst [marbleEarned, setMarbleEarned] = useState({ marbleId, earnedOn: format(new Date(), 'yyyy-MM-dd hh:mm')\t})\r\n\tconst [earnMarbleResult, earnMarble] = useMutation(earnMarbleMutation)\r\n\t\r\n\tconst handleInputChange = (event) => {\r\n const target = event.target;\r\n const value = target.type === 'checkbox' ? target.checked : target.value;\r\n const name = target.name;\r\n\r\n setMarbleEarned({\r\n\t\t\t...marbleEarned,\r\n [name]: value\r\n });\r\n\r\n\t}\r\n\r\n\tconst handleFinishButtonClick = () => {\r\n\t\tsaveEarnMarble()\r\n\t}\r\n\r\n\tconst saveEarnMarble = async () => {\t\t\r\n\t\tconst [isAuthenticated, user] = await Promise.all([authService.isAuthenticated(), authService.getUser()])\r\n\t\t\r\n\t\tlet userId = user.sub;\r\n\t\tlet marbleEarnedInput = {\r\n\t\t\t...marbleEarned,\r\n\t\t\tuserId\r\n\t\t}\r\n\t\t\r\n\t\tif (marbleEarnedInput.lengthOfTime)\r\n\t\t marbleEarnedInput.lengthOfTime = parseInt(marbleEarnedInput.lengthOfTime)\r\n\t\t\r\n\t\tconst variables = {\tmarbleEarnedInput\t}\r\n\r\n\t\tconst result = await earnMarble(variables)\r\n\t\t\r\n\t\tif (!result.error)\r\n\t\t\thistory.push('/earn')\r\n\t}\r\n\r\n\treturn (\r\n\t\t\r\n\t\t\t
Earn New Marble
\r\n\r\n\t\t\t
{marbleId}
\r\n\t\t\t
\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\r\n\r\n\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t