From d14f4572608e518a3e5ec109ceaed84ebf198d4c Mon Sep 17 00:00:00 2001 From: Alex Date: Fri, 6 Oct 2017 04:56:48 +0900 Subject: [PATCH 01/16] setup create-react-app --- .gitignore | 21 ++++ README.md | 2 + package.json | 16 +++ public/favicon.ico | Bin 0 -> 3870 bytes public/index.html | 40 +++++++ public/manifest.json | 15 +++ src/App.test.js | 8 ++ src/components/App.js | 9 ++ .../components/big_mac_2017_01.js | 0 src/index.css | 5 + src/index.js | 8 ++ src/logo.svg | 7 ++ src/registerServiceWorker.js | 108 ++++++++++++++++++ 13 files changed, 239 insertions(+) create mode 100644 .gitignore create mode 100644 package.json create mode 100644 public/favicon.ico create mode 100644 public/index.html create mode 100644 public/manifest.json create mode 100644 src/App.test.js create mode 100644 src/components/App.js rename big_mac_2017_01.js => src/components/big_mac_2017_01.js (100%) create mode 100644 src/index.css create mode 100644 src/index.js create mode 100644 src/logo.svg create mode 100644 src/registerServiceWorker.js diff --git a/.gitignore b/.gitignore new file mode 100644 index 00000000..d30f40ef --- /dev/null +++ b/.gitignore @@ -0,0 +1,21 @@ +# See https://help.github.com/ignore-files/ for more about ignoring files. + +# dependencies +/node_modules + +# testing +/coverage + +# production +/build + +# misc +.DS_Store +.env.local +.env.development.local +.env.test.local +.env.production.local + +npm-debug.log* +yarn-debug.log* +yarn-error.log* diff --git a/README.md b/README.md index dc85464b..e22fc7af 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,4 @@ # assignment_exchange_rates How much does a Big Mac cost in Italy? + +Alex Thomas diff --git a/package.json b/package.json new file mode 100644 index 00000000..9f7400d2 --- /dev/null +++ b/package.json @@ -0,0 +1,16 @@ +{ + "name": "assignment_exchange_rates", + "version": "0.1.0", + "private": true, + "dependencies": { + "react": "^16.0.0", + "react-dom": "^16.0.0", + "react-scripts": "1.0.14" + }, + "scripts": { + "start": "react-scripts start", + "build": "react-scripts build", + "test": "react-scripts test --env=jsdom", + "eject": "react-scripts eject" + } +} \ No newline at end of file diff --git a/public/favicon.ico b/public/favicon.ico new file mode 100644 index 0000000000000000000000000000000000000000..a11777cc471a4344702741ab1c8a588998b1311a GIT binary patch literal 3870 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 baj7?x%VD!5Cxk2YbYLNVeiXvvpMCWYo=by@ literal 0 HcmV?d00001 diff --git a/public/index.html b/public/index.html new file mode 100644 index 00000000..7bee0271 --- /dev/null +++ b/public/index.html @@ -0,0 +1,40 @@ + + + + + + + + + + + React App + + + +
+ + + diff --git a/public/manifest.json b/public/manifest.json new file mode 100644 index 00000000..be607e41 --- /dev/null +++ b/public/manifest.json @@ -0,0 +1,15 @@ +{ + "short_name": "React App", + "name": "Create React App Sample", + "icons": [ + { + "src": "favicon.ico", + "sizes": "192x192", + "type": "image/png" + } + ], + "start_url": "./index.html", + "display": "standalone", + "theme_color": "#000000", + "background_color": "#ffffff" +} diff --git a/src/App.test.js b/src/App.test.js new file mode 100644 index 00000000..b84af98d --- /dev/null +++ b/src/App.test.js @@ -0,0 +1,8 @@ +import React from 'react'; +import ReactDOM from 'react-dom'; +import App from './App'; + +it('renders without crashing', () => { + const div = document.createElement('div'); + ReactDOM.render(, div); +}); diff --git a/src/components/App.js b/src/components/App.js new file mode 100644 index 00000000..0b47f548 --- /dev/null +++ b/src/components/App.js @@ -0,0 +1,9 @@ +import React, { Component } from "react"; + +class App extends Component { + render() { + return
; + } +} + +export default App; diff --git a/big_mac_2017_01.js b/src/components/big_mac_2017_01.js similarity index 100% rename from big_mac_2017_01.js rename to src/components/big_mac_2017_01.js diff --git a/src/index.css b/src/index.css new file mode 100644 index 00000000..b4cc7250 --- /dev/null +++ b/src/index.css @@ -0,0 +1,5 @@ +body { + margin: 0; + padding: 0; + font-family: sans-serif; +} diff --git a/src/index.js b/src/index.js new file mode 100644 index 00000000..c7c23406 --- /dev/null +++ b/src/index.js @@ -0,0 +1,8 @@ +import React from "react"; +import ReactDOM from "react-dom"; +import "./index.css"; +import App from "./components/App"; +import registerServiceWorker from "./registerServiceWorker"; + +ReactDOM.render(, document.getElementById("root")); +registerServiceWorker(); diff --git a/src/logo.svg b/src/logo.svg new file mode 100644 index 00000000..6b60c104 --- /dev/null +++ b/src/logo.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/src/registerServiceWorker.js b/src/registerServiceWorker.js new file mode 100644 index 00000000..4a3ccf02 --- /dev/null +++ b/src/registerServiceWorker.js @@ -0,0 +1,108 @@ +// In production, we register a service worker to serve assets from local cache. + +// This lets the app load faster on subsequent visits in production, and gives +// it offline capabilities. However, it also means that developers (and users) +// will only see deployed updates on the "N+1" visit to a page, since previously +// cached resources are updated in the background. + +// To learn more about the benefits of this model, read https://goo.gl/KwvDNy. +// This link also includes instructions on opting out of this behavior. + +const isLocalhost = Boolean( + window.location.hostname === 'localhost' || + // [::1] is the IPv6 localhost address. + window.location.hostname === '[::1]' || + // 127.0.0.1/8 is considered localhost for IPv4. + window.location.hostname.match( + /^127(?:\.(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)){3}$/ + ) +); + +export default function register() { + if (process.env.NODE_ENV === 'production' && 'serviceWorker' in navigator) { + // The URL constructor is available in all browsers that support SW. + const publicUrl = new URL(process.env.PUBLIC_URL, window.location); + if (publicUrl.origin !== window.location.origin) { + // Our service worker won't work if PUBLIC_URL is on a different origin + // from what our page is served on. This might happen if a CDN is used to + // serve assets; see https://github.com/facebookincubator/create-react-app/issues/2374 + return; + } + + window.addEventListener('load', () => { + const swUrl = `${process.env.PUBLIC_URL}/service-worker.js`; + + if (!isLocalhost) { + // Is not local host. Just register service worker + registerValidSW(swUrl); + } else { + // This is running on localhost. Lets check if a service worker still exists or not. + checkValidServiceWorker(swUrl); + } + }); + } +} + +function registerValidSW(swUrl) { + navigator.serviceWorker + .register(swUrl) + .then(registration => { + registration.onupdatefound = () => { + const installingWorker = registration.installing; + installingWorker.onstatechange = () => { + if (installingWorker.state === 'installed') { + if (navigator.serviceWorker.controller) { + // At this point, the old content will have been purged and + // the fresh content will have been added to the cache. + // It's the perfect time to display a "New content is + // available; please refresh." message in your web app. + console.log('New content is available; please refresh.'); + } else { + // At this point, everything has been precached. + // It's the perfect time to display a + // "Content is cached for offline use." message. + console.log('Content is cached for offline use.'); + } + } + }; + }; + }) + .catch(error => { + console.error('Error during service worker registration:', error); + }); +} + +function checkValidServiceWorker(swUrl) { + // Check if the service worker can be found. If it can't reload the page. + fetch(swUrl) + .then(response => { + // Ensure service worker exists, and that we really are getting a JS file. + if ( + response.status === 404 || + response.headers.get('content-type').indexOf('javascript') === -1 + ) { + // No service worker found. Probably a different app. Reload the page. + navigator.serviceWorker.ready.then(registration => { + registration.unregister().then(() => { + window.location.reload(); + }); + }); + } else { + // Service worker found. Proceed as normal. + registerValidSW(swUrl); + } + }) + .catch(() => { + console.log( + 'No internet connection found. App is running in offline mode.' + ); + }); +} + +export function unregister() { + if ('serviceWorker' in navigator) { + navigator.serviceWorker.ready.then(registration => { + registration.unregister(); + }); + } +} From 32dd6ca6920d51220ffdca2285b4daaed47f4b1a Mon Sep 17 00:00:00 2001 From: Alex Date: Fri, 6 Oct 2017 17:22:36 +0900 Subject: [PATCH 02/16] project setup --- package.json | 3 +- public/index.html | 39 ++++++++++--------- src/components/App.js | 11 +++++- src/components/Converter.js | 10 +++++ src/components/CurrencyConverter.js | 9 +++++ src/components/CurrencyConverterContainer.js | 11 ++++++ src/components/CurrencyRatesBaseCurrency.js | 9 +++++ src/components/CurrencyRatesTable.js | 9 +++++ src/components/CurrencyRatesTableContainer.js | 10 +++++ src/components/elements/Alert.js | 13 +++++++ src/components/elements/Button.js | 23 +++++++++++ src/components/elements/Input.js | 15 +++++++ src/components/elements/InputGroup.js | 10 +++++ src/components/elements/JumbotronFluid.js | 17 ++++++++ src/components/elements/Showable.js | 11 ++++++ .../{ => elements}/big_mac_2017_01.js | 0 src/index.js | 1 + 17 files changed, 181 insertions(+), 20 deletions(-) create mode 100644 src/components/Converter.js create mode 100644 src/components/CurrencyConverter.js create mode 100644 src/components/CurrencyConverterContainer.js create mode 100644 src/components/CurrencyRatesBaseCurrency.js create mode 100644 src/components/CurrencyRatesTable.js create mode 100644 src/components/CurrencyRatesTableContainer.js create mode 100644 src/components/elements/Alert.js create mode 100644 src/components/elements/Button.js create mode 100644 src/components/elements/Input.js create mode 100644 src/components/elements/InputGroup.js create mode 100644 src/components/elements/JumbotronFluid.js create mode 100644 src/components/elements/Showable.js rename src/components/{ => elements}/big_mac_2017_01.js (100%) diff --git a/package.json b/package.json index 9f7400d2..70613fc3 100644 --- a/package.json +++ b/package.json @@ -3,6 +3,7 @@ "version": "0.1.0", "private": true, "dependencies": { + "bootstrap": "^4.0.0-alpha.6", "react": "^16.0.0", "react-dom": "^16.0.0", "react-scripts": "1.0.14" @@ -13,4 +14,4 @@ "test": "react-scripts test --env=jsdom", "eject": "react-scripts eject" } -} \ No newline at end of file +} diff --git a/public/index.html b/public/index.html index 7bee0271..85ed71bd 100644 --- a/public/index.html +++ b/public/index.html @@ -1,16 +1,17 @@ - - - - - - - - - React App - - - -
- - - + + + \ No newline at end of file diff --git a/src/components/App.js b/src/components/App.js index 0b47f548..3282dc13 100644 --- a/src/components/App.js +++ b/src/components/App.js @@ -1,8 +1,17 @@ import React, { Component } from "react"; +import CurrencyConverterContainer from "./CurrencyConverterContainer"; +import CurrencyRatesTableContainer from "./CurrencyRatesTableContainer"; +import JumbotronFluid from "./elements/JumbotronFluid"; class App extends Component { render() { - return
; + return ( +
+ + + +
+ ); } } diff --git a/src/components/Converter.js b/src/components/Converter.js new file mode 100644 index 00000000..2c2fd219 --- /dev/null +++ b/src/components/Converter.js @@ -0,0 +1,10 @@ +import React from "./react"; +import React, { Component } from "react"; + +class Converter extends Component { + render() { + return
; + } +} + +export default Converter; diff --git a/src/components/CurrencyConverter.js b/src/components/CurrencyConverter.js new file mode 100644 index 00000000..062ca920 --- /dev/null +++ b/src/components/CurrencyConverter.js @@ -0,0 +1,9 @@ +import React, { Component } from "react"; + +class CurrencyConverter extends Component { + render() { + return
; + } +} + +export default CurrencyConverter; diff --git a/src/components/CurrencyConverterContainer.js b/src/components/CurrencyConverterContainer.js new file mode 100644 index 00000000..c071fba7 --- /dev/null +++ b/src/components/CurrencyConverterContainer.js @@ -0,0 +1,11 @@ +import React, { Component } from "react"; +import CurrencyRatesBaseCurrency from "./CurrencyRatesBaseCurrency"; +import CurrencyConverter from "./CurrencyConverter"; + +class CurrencyConverterContainer extends Component { + render() { + return
; + } +} + +export default CurrencyConverterContainer; diff --git a/src/components/CurrencyRatesBaseCurrency.js b/src/components/CurrencyRatesBaseCurrency.js new file mode 100644 index 00000000..1adfc986 --- /dev/null +++ b/src/components/CurrencyRatesBaseCurrency.js @@ -0,0 +1,9 @@ +import React, { Component } from "react"; + +class CurrencyRatesBaseCurrency extends Component { + render() { + return
; + } +} + +export default CurrencyRatesBaseCurrency; diff --git a/src/components/CurrencyRatesTable.js b/src/components/CurrencyRatesTable.js new file mode 100644 index 00000000..c5ae7ad2 --- /dev/null +++ b/src/components/CurrencyRatesTable.js @@ -0,0 +1,9 @@ +import React, { Component } from "react"; + +class CurrenyRatesTable extends Component { + render() { + return
; + } +} + +export default CurrenyRatesTable; diff --git a/src/components/CurrencyRatesTableContainer.js b/src/components/CurrencyRatesTableContainer.js new file mode 100644 index 00000000..6f05f812 --- /dev/null +++ b/src/components/CurrencyRatesTableContainer.js @@ -0,0 +1,10 @@ +import React, { Component } from "react"; +import CurrencyRatesTable from "./CurrencyRatesTable"; + +class CurrencyRatesTableContainer extends Component { + render() { + return
; + } +} + +export default CurrencyRatesTableContainer; diff --git a/src/components/elements/Alert.js b/src/components/elements/Alert.js new file mode 100644 index 00000000..e6cdf49a --- /dev/null +++ b/src/components/elements/Alert.js @@ -0,0 +1,13 @@ +import React from 'react' + +const Alert = ({type, children}) => ( +
+ {children} +
+) + +Alert.defaultProps = { + type: 'success' +} + +export default Alert diff --git a/src/components/elements/Button.js b/src/components/elements/Button.js new file mode 100644 index 00000000..cbcbac0d --- /dev/null +++ b/src/components/elements/Button.js @@ -0,0 +1,23 @@ +import React from 'react' + +const Button = (props) => { + const {size, color, children, type} = props + const sizeClass = size ? `btn-${size}` : '' + + return ( + + ) +} + +Button.defaultProps = { + type: 'button', + color: 'default', + children: 'Submit', +} + +export default Button diff --git a/src/components/elements/Input.js b/src/components/elements/Input.js new file mode 100644 index 00000000..fe751c8d --- /dev/null +++ b/src/components/elements/Input.js @@ -0,0 +1,15 @@ +import React from 'react' + +const Input = (props) => { + const classNames = `form-control ${props.className}` + + return ( + + ) +} + +Input.defaultProps = { + type: 'text' +} + +export default Input diff --git a/src/components/elements/InputGroup.js b/src/components/elements/InputGroup.js new file mode 100644 index 00000000..3b7e126b --- /dev/null +++ b/src/components/elements/InputGroup.js @@ -0,0 +1,10 @@ +import React from 'react' + +const InputGroup = ({name, labelText, children}) => ( +
+ + {children} +
+) + +export default InputGroup diff --git a/src/components/elements/JumbotronFluid.js b/src/components/elements/JumbotronFluid.js new file mode 100644 index 00000000..3c2c6f91 --- /dev/null +++ b/src/components/elements/JumbotronFluid.js @@ -0,0 +1,17 @@ +import React from 'react' +import Showable from './Showable' + +const JumbotronFluid = ({heading, lead}) => ( +
+
+ +

{heading}

+
+ +

{lead}

+
+
+
+) + +export default JumbotronFluid diff --git a/src/components/elements/Showable.js b/src/components/elements/Showable.js new file mode 100644 index 00000000..11872e3a --- /dev/null +++ b/src/components/elements/Showable.js @@ -0,0 +1,11 @@ +import React from "react"; + +const Showable = ({ show, children }) => { + if (!show) { + return null; + } + + return
{children}
; +}; + +export default Showable; diff --git a/src/components/big_mac_2017_01.js b/src/components/elements/big_mac_2017_01.js similarity index 100% rename from src/components/big_mac_2017_01.js rename to src/components/elements/big_mac_2017_01.js diff --git a/src/index.js b/src/index.js index c7c23406..f8f271ca 100644 --- a/src/index.js +++ b/src/index.js @@ -1,5 +1,6 @@ import React from "react"; import ReactDOM from "react-dom"; +import "bootstrap/dist/css/bootstrap.css"; import "./index.css"; import App from "./components/App"; import registerServiceWorker from "./registerServiceWorker"; From 9531fc9d97e4f620f96de41fa6246089bb213704 Mon Sep 17 00:00:00 2001 From: Alex Date: Fri, 6 Oct 2017 20:09:42 +0900 Subject: [PATCH 03/16] setup before api requests --- src/components/App.js | 36 +++++++++++++++++-- src/components/BaseCurrencyForm.js | 29 +++++++++++++++ src/components/Converter.js | 10 ------ src/components/CurrencyConverterContainer.js | 1 - src/components/CurrencyRatesBaseCurrency.js | 9 ----- src/components/CurrencyRatesTable.js | 9 ++--- src/components/CurrencyRatesTableContainer.js | 8 ++++- src/components/elements/Converter.js | 12 +++++++ src/components/elements/InputGroup.js | 8 ++--- src/components/elements/Select.js | 23 ++++++++++++ src/components/elements/Table.js | 23 ++++++++++++ 11 files changed, 135 insertions(+), 33 deletions(-) create mode 100644 src/components/BaseCurrencyForm.js delete mode 100644 src/components/Converter.js delete mode 100644 src/components/CurrencyRatesBaseCurrency.js create mode 100644 src/components/elements/Converter.js create mode 100644 src/components/elements/Select.js create mode 100644 src/components/elements/Table.js diff --git a/src/components/App.js b/src/components/App.js index 3282dc13..c610bcdc 100644 --- a/src/components/App.js +++ b/src/components/App.js @@ -4,12 +4,44 @@ import CurrencyRatesTableContainer from "./CurrencyRatesTableContainer"; import JumbotronFluid from "./elements/JumbotronFluid"; class App extends Component { + constructor() { + super(), + (this.state = { + isFetching: false, + baseCurrency: "EUR", + baseValue: 1, + exchangeRate: 0.8, + convertedValue: "", + convertedCurrency: "USD" + }); + } + populateCurrencyTable = e => { + console.log(e.target); + }; render() { + const { + isFetching, + baseCurrency, + baseValue, + exchangeRate, + convertedValue, + convertedCurrency + } = this.state; return (
- - + +
); } diff --git a/src/components/BaseCurrencyForm.js b/src/components/BaseCurrencyForm.js new file mode 100644 index 00000000..b0bdddc2 --- /dev/null +++ b/src/components/BaseCurrencyForm.js @@ -0,0 +1,29 @@ +import React from "react"; +import Select from "./elements/Select"; +import Button from "./elements/Button"; + +const BaseCurrencyForm = props => { + const { onSubmit } = props; + + return ( +
+ +
+
+ ); }; export default CurrencyConverterForm; From 30f8e9d0af7fc996669478f3963817b6cae28b8c Mon Sep 17 00:00:00 2001 From: Alex Date: Tue, 10 Oct 2017 21:29:22 +0900 Subject: [PATCH 10/16] commit before branching to improve converter components. State separation is not optimal --- src/components/App.js | 6 +- src/components/BaseCurrencyForm.js | 12 +- .../ConverterBaseCurrencySelector.js | 20 +++ .../ConverterConvertedCurrencySelector.js | 21 +++ src/components/CurrencyConverterContainer.js | 36 +++--- src/components/CurrencyConverterForm.js | 121 ++++++++++++------ src/components/elements/Select.js | 16 +-- 7 files changed, 155 insertions(+), 77 deletions(-) create mode 100644 src/components/ConverterBaseCurrencySelector.js create mode 100644 src/components/ConverterConvertedCurrencySelector.js diff --git a/src/components/App.js b/src/components/App.js index 5e03300a..680c4de0 100644 --- a/src/components/App.js +++ b/src/components/App.js @@ -18,7 +18,6 @@ class App extends Component { }); } getRates = () => { - console.log("hit"); fetch( `http://api.fixer.io/${this.state.date}?base=${this.state.baseCurrency}` ) @@ -76,7 +75,6 @@ class App extends Component { }); }; render() { - console.log("this"); const { baseCurrency, baseValue, @@ -86,7 +84,8 @@ class App extends Component { rates, date } = this.state; - console.log("RATES Passed", rates); + const currenciesArray = Object.keys(rates); + //console.log("RATES Passed", rates); return (
@@ -97,6 +96,7 @@ class App extends Component { setDate={this.setDate} date={date} rates={rates} + currenciesArray={currenciesArray} />
diff --git a/src/components/BaseCurrencyForm.js b/src/components/BaseCurrencyForm.js index 9909b1f8..5a9e2cfd 100644 --- a/src/components/BaseCurrencyForm.js +++ b/src/components/BaseCurrencyForm.js @@ -3,8 +3,14 @@ import Select from "./elements/Select"; import Button from "./elements/Button"; const BaseCurrencyForm = props => { - const { rates, baseCurrency, switch_currency, setDate, date } = props; - console.log(rates); + const { + rates, + baseCurrency, + switch_currency, + setDate, + date, + currenciesArray + } = props; return (
{ + //currenciesArray.unshift(converterBaseCurrency); + return ( + + ); +}; + +export default ConverterConvertedCurrencySelector; diff --git a/src/components/CurrencyConverterContainer.js b/src/components/CurrencyConverterContainer.js index 1d8bebbb..3c891149 100644 --- a/src/components/CurrencyConverterContainer.js +++ b/src/components/CurrencyConverterContainer.js @@ -3,15 +3,15 @@ import CurrencyConverterForm from "./CurrencyConverterForm"; class CurrencyConverterContainer extends Component { constructor(props) { - super(props), - (this.state = { - isFetching: false, - converterBaseCurrency: "USD", - converterBaseValue: 1, - convertedCurrency: "EUR", - convertedValue: "", - converterExchangeRate: 0.0 - }); + super(props); + this.state = { + isFetching: false, + converterBaseCurrency: "USD", + converterBaseValue: 1, + convertedCurrency: "EUR", + convertedValue: "", + converterExchangeRate: 0.0 + }; } baseCurrencyInput = e => { let input = e.target.value; @@ -27,24 +27,14 @@ class CurrencyConverterContainer extends Component { return response.json(); }) .then(json => { - console.log("Calculator Fetch", json.rates[converted]); + //console.log("Calculator Fetch", json.rates[converted]); this.setState({ isFetching: false, converterExchangeRate: json.rates[converted] }); }); }; - selectCurrency = e => { - //console.log("select-target", e.target); - //console.log("select-target.value", e.target.value); - return new Promise((resolve, reject) => { - resolve( - this.setState({ - converterBaseCurrency: e.target.value - }) - ); - }); - }; + render() { const { converterBaseCurrency, @@ -59,10 +49,14 @@ class CurrencyConverterContainer extends Component { ); } } +``; export default CurrencyConverterContainer; diff --git a/src/components/CurrencyConverterForm.js b/src/components/CurrencyConverterForm.js index a226cf71..37be9e83 100644 --- a/src/components/CurrencyConverterForm.js +++ b/src/components/CurrencyConverterForm.js @@ -1,45 +1,84 @@ -import React from "react"; +import React, { Component } from "react"; import Input from "./elements/Input"; -import Select from "./elements/Select"; +import ConverterBaseCurrencySelector from "./ConverterBaseCurrencySelector"; +import ConverterConvertedCurrencySelector from "./ConverterConvertedCurrencySelector"; -const CurrencyConverterForm = props => { - const { - converterBaseCurrency, - convertedCurrency, - converterBaseValue, - convertedValue, - baseCurrencyInput, - converterExchangeRate, - selectCurrency - } = props; - return ( -
- - - {/* - - - */} - -
- ); -}; +class CurrencyConverterForm extends Component { + constructor(props) { + super(props); + this.state = { + currenciesArray: [], + converterBaseCurrency: "USD", + convertedCurrency: "EUR" + }; + } + componentDidMount = () => { + //gets array of currencies for currency selectors + this.setState({ + isFetching: true + }); + fetch(`http://api.fixer.io/latest?base=USD`) + .then(response => { + return response.json(); + }) + .then(json => { + console.log("FETCHING", json.rates); + json.rates.USD = "USD"; + this.setState({ + isFetching: false, + currenciesArray: Object.keys(json.rates) + }); + //this.props.converterBaseCurrency = this.state.converterBaseCurrency; + }); + }; + + selectBaseCurrency = e => { + //console.log("select-target", e.target); + //console.log("select-target.value", e.target.value); + this.setState({ converterBaseCurrency: e.target.value }); + }; + selectConvertedCurrency = e => { + //console.log("select-target", e.target); + //console.log("select-target.value", e.target.value); + this.setState({ convertedCurrency: e.target.value }); + }; + render() { + const { + converterBaseValue, + convertedValue, + baseCurrencyInput, + converterExchangeRate + } = this.props; + const { + convertedCurrency, + converterBaseCurrency, + currenciesArray + } = this.state; + console.log("C_array", currenciesArray); + return ( +
+
+ + +

to

+ + +
+ ); + } +} export default CurrencyConverterForm; diff --git a/src/components/elements/Select.js b/src/components/elements/Select.js index 160bce16..1453e8a7 100644 --- a/src/components/elements/Select.js +++ b/src/components/elements/Select.js @@ -1,16 +1,14 @@ import React from "react"; const Select = props => { - //const { baseCurrency, rates, switch_currency } = props; - const { baseValue, handleSwitch, rates } = props; + const { baseValue, handleSwitch, data } = props; - //gets currencies from rates object - let currenciesArray = Object.keys(rates); - //console.log("log rates select", rates); - const currenciesOptions = currenciesArray.map((currency, i) => { + //gets keys from dataObject + //console.log("DAATA", data); + const optionsList = data.map((item, i) => { return ( - ); }); @@ -24,7 +22,7 @@ const Select = props => { - {currenciesOptions} + {optionsList} ); }; From 95e34244ffe60956f7499bd6912fc4f3499872a7 Mon Sep 17 00:00:00 2001 From: Alex Date: Tue, 10 Oct 2017 22:37:11 +0900 Subject: [PATCH 11/16] cleaned up state in branched converter --- src/components/App.js | 1 - src/components/CurrencyConverterContainer.js | 99 ++++++++++++++------ src/components/CurrencyConverterForm.js | 83 ---------------- 3 files changed, 68 insertions(+), 115 deletions(-) diff --git a/src/components/App.js b/src/components/App.js index 680c4de0..6a7b8de4 100644 --- a/src/components/App.js +++ b/src/components/App.js @@ -23,7 +23,6 @@ class App extends Component { ) .then(response => response.json()) .then(json => { - console.log("RAATES", json.rates); this.setState({ rates: json.rates, isFetching: false diff --git a/src/components/CurrencyConverterContainer.js b/src/components/CurrencyConverterContainer.js index 3c891149..7f2df604 100644 --- a/src/components/CurrencyConverterContainer.js +++ b/src/components/CurrencyConverterContainer.js @@ -1,62 +1,99 @@ import React, { Component } from "react"; -import CurrencyConverterForm from "./CurrencyConverterForm"; +import Input from "./elements/Input"; +import ConverterBaseCurrencySelector from "./ConverterBaseCurrencySelector"; +import ConverterConvertedCurrencySelector from "./ConverterConvertedCurrencySelector"; class CurrencyConverterContainer extends Component { constructor(props) { super(props); this.state = { - isFetching: false, converterBaseCurrency: "USD", - converterBaseValue: 1, convertedCurrency: "EUR", - convertedValue: "", - converterExchangeRate: 0.0 + converterBaseValue: 1, + currenciesArray: [] }; } - baseCurrencyInput = e => { - let input = e.target.value; - this.setState({ converterBaseValue: input }); - }; - componentDidMount = () => { - //sets new state of rates - this.setState({ isFetching: true }); - let base = this.state.converterBaseCurrency; - let converted = this.state.convertedCurrency; - fetch(`http://api.fixer.io/latest?base=${base}&symbols=${converted}`) + + //gets array of currencies for currency selectors + //will take the base currency + getCurrencies = base => { + this.setState({ + isFetching: true + }); + fetch(`http://api.fixer.io/latest?base=${base}`) .then(response => { return response.json(); }) .then(json => { - //console.log("Calculator Fetch", json.rates[converted]); + console.log("Fetched selector currencies"); this.setState({ isFetching: false, - converterExchangeRate: json.rates[converted] + currenciesArray: Object.keys(json.rates) }); }); }; - + // component did mount with api call to populate selectors + componentDidMount = () => { + this.getCurrencies(this.state.converterBaseCurrency); + }; + //another api call to get rates for selected currencies + //will take base cuurency and the converted currency + baseCurrencyInput = e => { + let input = e.target.value; + this.setState({ converterBaseValue: input }); + }; + selectBaseCurrency = e => { + this.setState({ converterBaseCurrency: e.target.value }); + this.getCurrencies(e.target.value); + }; + selectConvertedCurrency = e => { + this.setState({ convertedCurrency: e.target.value }); + this.getCurrencies(e.target.value); + }; render() { const { converterBaseCurrency, - converterBaseValue, convertedCurrency, - convertedValue, - converterExchangeRate + converterBaseValue, + currenciesArray } = this.state; + console.log("rendered"); return ( -
-

Currency Converter

- +
+
+ + +

to

+ + + {/* + input up + select up + p to + select + button + + + rate

+ + Output + */}
); } } -``; export default CurrencyConverterContainer; diff --git a/src/components/CurrencyConverterForm.js b/src/components/CurrencyConverterForm.js index 37be9e83..5b563432 100644 --- a/src/components/CurrencyConverterForm.js +++ b/src/components/CurrencyConverterForm.js @@ -1,84 +1 @@ import React, { Component } from "react"; -import Input from "./elements/Input"; -import ConverterBaseCurrencySelector from "./ConverterBaseCurrencySelector"; -import ConverterConvertedCurrencySelector from "./ConverterConvertedCurrencySelector"; - -class CurrencyConverterForm extends Component { - constructor(props) { - super(props); - this.state = { - currenciesArray: [], - converterBaseCurrency: "USD", - convertedCurrency: "EUR" - }; - } - componentDidMount = () => { - //gets array of currencies for currency selectors - this.setState({ - isFetching: true - }); - fetch(`http://api.fixer.io/latest?base=USD`) - .then(response => { - return response.json(); - }) - .then(json => { - console.log("FETCHING", json.rates); - json.rates.USD = "USD"; - this.setState({ - isFetching: false, - currenciesArray: Object.keys(json.rates) - }); - //this.props.converterBaseCurrency = this.state.converterBaseCurrency; - }); - }; - - selectBaseCurrency = e => { - //console.log("select-target", e.target); - //console.log("select-target.value", e.target.value); - this.setState({ converterBaseCurrency: e.target.value }); - }; - selectConvertedCurrency = e => { - //console.log("select-target", e.target); - //console.log("select-target.value", e.target.value); - this.setState({ convertedCurrency: e.target.value }); - }; - render() { - const { - converterBaseValue, - convertedValue, - baseCurrencyInput, - converterExchangeRate - } = this.props; - const { - convertedCurrency, - converterBaseCurrency, - currenciesArray - } = this.state; - console.log("C_array", currenciesArray); - return ( -
-
- - -

to

- - -
- ); - } -} - -export default CurrencyConverterForm; From e31da199797f563c0b423993f83525823412b2ce Mon Sep 17 00:00:00 2001 From: Alex Date: Wed, 11 Oct 2017 03:11:44 +0900 Subject: [PATCH 12/16] added some styles, reconfigured fetch --- src/components/App.js | 1 + src/components/CurrencyConverterContainer.js | 66 ++++++++++++++------ src/components/CurrencyConverterForm.js | 46 +++++++++++++- src/components/CurrencyConverterOutput.js | 20 ++++++ src/components/elements/Input.js | 18 +++--- src/index.css | 48 +++++++++++++- 6 files changed, 167 insertions(+), 32 deletions(-) create mode 100644 src/components/CurrencyConverterOutput.js diff --git a/src/components/App.js b/src/components/App.js index 6a7b8de4..0493cf6f 100644 --- a/src/components/App.js +++ b/src/components/App.js @@ -97,6 +97,7 @@ class App extends Component { rates={rates} currenciesArray={currenciesArray} /> +
); diff --git a/src/components/CurrencyConverterContainer.js b/src/components/CurrencyConverterContainer.js index 7f2df604..a1dc4d13 100644 --- a/src/components/CurrencyConverterContainer.js +++ b/src/components/CurrencyConverterContainer.js @@ -1,7 +1,7 @@ import React, { Component } from "react"; import Input from "./elements/Input"; -import ConverterBaseCurrencySelector from "./ConverterBaseCurrencySelector"; -import ConverterConvertedCurrencySelector from "./ConverterConvertedCurrencySelector"; +import CurrencyConverterForm from "./CurrencyConverterForm"; +import CurrencyConverterOutput from "./CurrencyConverterOutput"; class CurrencyConverterContainer extends Component { constructor(props) { @@ -10,7 +10,9 @@ class CurrencyConverterContainer extends Component { converterBaseCurrency: "USD", convertedCurrency: "EUR", converterBaseValue: 1, - currenciesArray: [] + currenciesArray: [], + convertingRate: 1, + convertingOutcome: 0 }; } @@ -38,6 +40,32 @@ class CurrencyConverterContainer extends Component { }; //another api call to get rates for selected currencies //will take base cuurency and the converted currency + + handleClick = e => { + e.preventDefault(); + this.setState({ + isFetching: true + }); + fetch( + `http://api.fixer.io/latest?base=${this.state + .converterBaseCurrency}&symbols=${this.state.convertedCurrency}` + ) + .then(response => response.json()) + .then(json => { + let rate = Object.values(json.rates)[0]; + this.setState( + { + convertingRate: rate + }, + () => { + this.setState({ + convertingOutcome: + this.state.converterBaseValue * this.state.convertingRate + }); + } + ); + }); + }; baseCurrencyInput = e => { let input = e.target.value; this.setState({ converterBaseValue: input }); @@ -55,29 +83,27 @@ class CurrencyConverterContainer extends Component { converterBaseCurrency, convertedCurrency, converterBaseValue, - currenciesArray + currenciesArray, + convertingRate, + convertingOutcome } = this.state; console.log("rendered"); return (
+

Currency Calculator

- - -

to

- +
+

Rate:

+

{convertingRate}

+
+ {/* input up diff --git a/src/components/CurrencyConverterForm.js b/src/components/CurrencyConverterForm.js index 5b563432..3fb7d865 100644 --- a/src/components/CurrencyConverterForm.js +++ b/src/components/CurrencyConverterForm.js @@ -1 +1,45 @@ -import React, { Component } from "react"; +import React from "react"; +import Input from "./elements/Input"; +import ConverterBaseCurrencySelector from "./ConverterBaseCurrencySelector"; +import ConverterConvertedCurrencySelector from "./ConverterConvertedCurrencySelector"; + +const CurrencyConverterForm = ({ + converterBaseCurrency, + selectBaseCurrency, + currenciesArray, //for populating selectors + convertedCurrency, //second selector + selectConvertedCurrency, //function upon selection + converterBaseValue, //value of user input + baseCurrencyInput, //function changes converterBaseValue upon user input + handleClick //function for submit btn +}) => { + return ( +
+ + +

to

+ + +
+ ); +}; + +export default CurrencyConverterForm; diff --git a/src/components/CurrencyConverterOutput.js b/src/components/CurrencyConverterOutput.js new file mode 100644 index 00000000..32f16a5c --- /dev/null +++ b/src/components/CurrencyConverterOutput.js @@ -0,0 +1,20 @@ +import React from "react"; + +const CurrencyConverterOutput = ({ + converterBaseValue, + converterBaseCurrency, + convertingOutcome, + convertedCurrency +}) => { + return ( +
+

{converterBaseValue}

+

{converterBaseCurrency}

+

=

+

{convertingOutcome}

+

{convertedCurrency}

+
+ ); +}; + +export default CurrencyConverterOutput; diff --git a/src/components/elements/Input.js b/src/components/elements/Input.js index fe751c8d..43ae7332 100644 --- a/src/components/elements/Input.js +++ b/src/components/elements/Input.js @@ -1,15 +1,13 @@ -import React from 'react' +import React from "react"; -const Input = (props) => { - const classNames = `form-control ${props.className}` +const Input = props => { + const classNames = `form-control ${props.className}`; - return ( - - ) -} + return ; +}; Input.defaultProps = { - type: 'text' -} + type: "text" +}; -export default Input +export default Input; diff --git a/src/index.css b/src/index.css index 3924fb4b..5e51d11f 100644 --- a/src/index.css +++ b/src/index.css @@ -5,7 +5,7 @@ body { } .currency_table { - width: 70%; + width: 90%; margin: 2rem auto; max-height: 15rem; overflow: auto; @@ -15,3 +15,49 @@ body { width: 50%; margin: 3rem auto; } + +section h1 { + width: 50%; + margin: 3rem auto; + text-decoration: none; +} + +.converter_wrapper { + text-align: center; +} + +#currencyConverterForm { + outline: 1px solid gray; + padding-top: 0.5rem; +} + +#currencyConverterForm input, +#currencyConverterForm select { + width: 5rem; + height: 2.5rem; + margin: 0.5rem 1.5rem; +} +.converter_get_input { + display: flex; + flex-wrap: wrap; + width: fit-content; + margin: 0.5rem auto; +} +#converter_to { + font-family: sans-serif; + margin: -0.1rem 3rem; + font-size: 2rem; + font-style: italic; + font-weight: 500; +} + +.rate { + display: flex; + width: fit-content; + margin: 0.5rem auto; +} + +.rate p { + margin: 0 2rem; + font-size: 2rem; +} From ec827146b59d80ca3d3e59079f342bba3ef5dfe6 Mon Sep 17 00:00:00 2001 From: Alex Date: Wed, 11 Oct 2017 03:49:44 +0900 Subject: [PATCH 13/16] applied basic style and layout --- src/components/CurrencyConverterContainer.js | 7 ++- src/index.css | 57 +++++++++++++++++--- 2 files changed, 54 insertions(+), 10 deletions(-) diff --git a/src/components/CurrencyConverterContainer.js b/src/components/CurrencyConverterContainer.js index a1dc4d13..da789ee1 100644 --- a/src/components/CurrencyConverterContainer.js +++ b/src/components/CurrencyConverterContainer.js @@ -58,9 +58,12 @@ class CurrencyConverterContainer extends Component { convertingRate: rate }, () => { + let outcome = + this.state.converterBaseValue * this.state.convertingRate; + let length = this.state.convertedBaseValue + 3; + outcome = outcome.toFixed(3); this.setState({ - convertingOutcome: - this.state.converterBaseValue * this.state.convertingRate + convertingOutcome: outcome }); } ); diff --git a/src/index.css b/src/index.css index 5e51d11f..b554f4b6 100644 --- a/src/index.css +++ b/src/index.css @@ -9,35 +9,67 @@ body { margin: 2rem auto; max-height: 15rem; overflow: auto; + font-size: 1.2rem; +} +.currency_table * { + margin: 0 auto; +} +.currency_table th { + width: 1%; } - #ChooseBaseCurrency { - width: 50%; - margin: 3rem auto; + width: 90%; + text-align: center; +} + +#ChooseBaseCurrency * { + width: 30%; + margin: 0.5rem 3rem; + display: inline-block; + font-size: 1.5rem; +} +@media (max-width: 865px) { + #ChooseBaseCurrency * { + width: 60%; + margin: 1rem 3rem; + display: inline-block; + font-size: 1.5rem; + } + .currency_table { + width: 92%; + margin: 1rem auto; + max-height: fit-content; + font-size: 1rem; + } } section h1 { width: 50%; - margin: 3rem auto; + margin: 5rem auto; text-decoration: none; + background-color: #9fbcdf; + outline: 38px solid #9fbcdf; } .converter_wrapper { text-align: center; + margin-top: 3rem; } #currencyConverterForm { - outline: 1px solid gray; - padding-top: 0.5rem; + outline: 1px solid #d9d8d8; + padding: 0.5rem; + margin-bottom: 8rem; } #currencyConverterForm input, #currencyConverterForm select { - width: 5rem; + width: 8rem; height: 2.5rem; margin: 0.5rem 1.5rem; } -.converter_get_input { +.converter_get_input, +.outcome { display: flex; flex-wrap: wrap; width: fit-content; @@ -61,3 +93,12 @@ section h1 { margin: 0 2rem; font-size: 2rem; } + +.outcome { + border: 2px solid #6ec2ba; + margin: 2rem auto; +} +.outcome p { + width: 10rem; + font-size: 2rem; +} From c04db1d08d547050487f55057c2f2d37393de116 Mon Sep 17 00:00:00 2001 From: Alex Date: Wed, 11 Oct 2017 14:35:42 +0900 Subject: [PATCH 14/16] more state clean up on App.js --- src/components/App.js | 55 ++++++-------------- src/components/CurrencyConverterContainer.js | 2 +- 2 files changed, 16 insertions(+), 41 deletions(-) diff --git a/src/components/App.js b/src/components/App.js index 0493cf6f..1e217bee 100644 --- a/src/components/App.js +++ b/src/components/App.js @@ -9,10 +9,6 @@ class App extends Component { (this.state = { isFetching: false, baseCurrency: "USD", - baseValue: 1, - exchangeRate: 0.8, - convertedValue: "", - convertedCurrency: "EUR", rates: [], date: new Date().toISOString().slice(0, 10) }); @@ -31,8 +27,7 @@ class App extends Component { }; componentDidMount() { // Before performing the fetch, set isFetching to true - this.setState({ isFetching: true }); - this.getRates(); + this.setState({ isFetching: true }, this.getRates()); } shouldComponentUpdate() { return this.state.isFetching !== false; @@ -42,47 +37,27 @@ class App extends Component { e.preventDefault(); //console.log("select-target", e.target); //console.log("select-target.value", e.target.value); - return new Promise((resolve, reject) => { - resolve( - this.setState({ - baseCurrency: e.target.value - }) - ); - }).then(() => { - //console.log("hit"); - //console.log("RAAATES", this.state.rates); - this.setState({ isFetching: true }); - this.getRates(); - }); + this.setState( + { + baseCurrency: e.target.value + }, + this.setState({ isFetching: true }, this.getRates()) + ); }; setDate = e => { //console.log("date-target", e.target); //console.log("date-target.value", e.target.value); - - return new Promise((resolve, reject) => { - resolve( - this.setState({ - date: e.target.value - }) - ); - }).then(() => { - //console.log("hit"); - //console.log("RAAATES", this.state.rates); - this.setState({ isFetching: true }); - this.getRates(); - }); + this.setState( + { + date: e.target.value, + isFetching: true + }, + this.getRates() + ); }; render() { - const { - baseCurrency, - baseValue, - exchangeRate, - convertedValue, - convertedCurrency, - rates, - date - } = this.state; + const { baseCurrency, rates, date } = this.state; const currenciesArray = Object.keys(rates); //console.log("RATES Passed", rates); return ( diff --git a/src/components/CurrencyConverterContainer.js b/src/components/CurrencyConverterContainer.js index da789ee1..1f716117 100644 --- a/src/components/CurrencyConverterContainer.js +++ b/src/components/CurrencyConverterContainer.js @@ -11,7 +11,7 @@ class CurrencyConverterContainer extends Component { convertedCurrency: "EUR", converterBaseValue: 1, currenciesArray: [], - convertingRate: 1, + convertingRate: "", convertingOutcome: 0 }; } From 6eed5b2b14109d5d062bb9b82e84ebfc9e4655f1 Mon Sep 17 00:00:00 2001 From: Alex Date: Wed, 11 Oct 2017 15:16:59 +0900 Subject: [PATCH 15/16] proptype valdation added --- .../ConverterBaseCurrencySelector.js | 5 +++++ .../ConverterConvertedCurrencySelector.js | 7 +++++++ src/components/CurrencyConverterContainer.js | 21 ++++++++----------- src/components/CurrencyConverterForm.js | 12 +++++++++++ src/components/CurrencyConverterOutput.js | 17 +++++++++++++++ 5 files changed, 50 insertions(+), 12 deletions(-) diff --git a/src/components/ConverterBaseCurrencySelector.js b/src/components/ConverterBaseCurrencySelector.js index f933d71a..f7665ccc 100644 --- a/src/components/ConverterBaseCurrencySelector.js +++ b/src/components/ConverterBaseCurrencySelector.js @@ -17,4 +17,9 @@ const ConverterBaseCurrencySelector = ({ ); }; +ConverterConvertedCurrencySelector.propTypes = { + convertedCurrency: PropTypes.string.isRequired, + selectCurrency: PropTypes.func.isRequired, + currenciesArray: PropTypes.array.isRequired +}; export default ConverterBaseCurrencySelector; diff --git a/src/components/ConverterConvertedCurrencySelector.js b/src/components/ConverterConvertedCurrencySelector.js index 28d049dc..b0de2582 100644 --- a/src/components/ConverterConvertedCurrencySelector.js +++ b/src/components/ConverterConvertedCurrencySelector.js @@ -1,5 +1,6 @@ import React from "react"; import Select from "./elements/Select"; +import PropTypes from "prop-types"; const ConverterConvertedCurrencySelector = ({ selectCurrency, @@ -18,4 +19,10 @@ const ConverterConvertedCurrencySelector = ({ ); }; +ConverterConvertedCurrencySelector.propTypes = { + convertedCurrency: PropTypes.string.isRequired, + selectCurrency: PropTypes.func.isRequired, + currenciesArray: PropTypes.array.isRequired +}; + export default ConverterConvertedCurrencySelector; diff --git a/src/components/CurrencyConverterContainer.js b/src/components/CurrencyConverterContainer.js index 1f716117..ca5b8503 100644 --- a/src/components/CurrencyConverterContainer.js +++ b/src/components/CurrencyConverterContainer.js @@ -2,6 +2,7 @@ import React, { Component } from "react"; import Input from "./elements/Input"; import CurrencyConverterForm from "./CurrencyConverterForm"; import CurrencyConverterOutput from "./CurrencyConverterOutput"; +import PropTypes from "prop-types"; class CurrencyConverterContainer extends Component { constructor(props) { @@ -108,21 +109,17 @@ class CurrencyConverterContainer extends Component {
- {/* - input up - select up - p to - select - button - - - rate

- - Output - */} ); } } +CurrencyConverterContainer.propTypes = { + converterBaseCurrency: PropTypes.string.isRequired, + convertedCurrency: PropTypes.string.isRequired, + converterBaseValue: PropTypes.number, + currenciesArray: PropTypes.array.isRequired, + convertingRate: PropTypes.number, + convertingOutcome: PropTypes.number +}; export default CurrencyConverterContainer; diff --git a/src/components/CurrencyConverterForm.js b/src/components/CurrencyConverterForm.js index 3fb7d865..f1bd0a70 100644 --- a/src/components/CurrencyConverterForm.js +++ b/src/components/CurrencyConverterForm.js @@ -2,6 +2,7 @@ import React from "react"; import Input from "./elements/Input"; import ConverterBaseCurrencySelector from "./ConverterBaseCurrencySelector"; import ConverterConvertedCurrencySelector from "./ConverterConvertedCurrencySelector"; +import PropTypes from "prop-types"; const CurrencyConverterForm = ({ converterBaseCurrency, @@ -42,4 +43,15 @@ const CurrencyConverterForm = ({ ); }; +CurrencyConverterForm.propTypes = { + converterBaseCurrency: PropTypes.string.isRequired, + selectBaseCurrency: PropTypes.string.isRequired, + currenciesArray: PropTypes.array.isRequired, + convertedCurrency: PropTypes.string.isRequired, + selectConvertedCurrency: PropTypes.func.isRequired, + converterBaseValue: PropTypes.number, + baseCurrencyInput: PropTypes.func.isRequired, + handleClick: PropTypes.func.isRequired +}; + export default CurrencyConverterForm; diff --git a/src/components/CurrencyConverterOutput.js b/src/components/CurrencyConverterOutput.js index 32f16a5c..f69174e0 100644 --- a/src/components/CurrencyConverterOutput.js +++ b/src/components/CurrencyConverterOutput.js @@ -1,4 +1,5 @@ import React from "react"; +import PropTypes from "prop-types"; const CurrencyConverterOutput = ({ converterBaseValue, @@ -17,4 +18,20 @@ const CurrencyConverterOutput = ({ ); }; +CurrencyConverterOutput.propTypes = { + converterBaseValue: PropTypes.number, + converterBaseCurrency: PropTypes.string.isRequired, + convertingOutcome: PropTypes.number, + convertedCurrency: PropTypes.string.isRequired, + customConverterBaseValue: function( + props, + converterBaseValue, + CurrencyConverterOutput + ) { + if (typeof converterBaseValue !== "number") { + return new Error("Value must be a number"); + } + } +}; + export default CurrencyConverterOutput; From cdd566313e63912fad69a229be8113fce6798332 Mon Sep 17 00:00:00 2001 From: Alex Date: Fri, 29 Jun 2018 23:09:33 +0900 Subject: [PATCH 16/16] added api key in config file --- .gitignore | 2 + public/index.html | 4 +- src/components/App.js | 7 +- src/components/BaseCurrencyForm.js | 62 ++++----- .../ConverterBaseCurrencySelector.js | 37 +++--- .../ConverterConvertedCurrencySelector.js | 32 ++--- ...rOutput.js => CurrencyConverterOutput.jsx} | 0 src/components/elements/Table.js | 42 +++---- src/index.css | 118 +++++++++--------- 9 files changed, 156 insertions(+), 148 deletions(-) rename src/components/{CurrencyConverterOutput.js => CurrencyConverterOutput.jsx} (100%) diff --git a/.gitignore b/.gitignore index d30f40ef..33812f55 100644 --- a/.gitignore +++ b/.gitignore @@ -19,3 +19,5 @@ npm-debug.log* yarn-debug.log* yarn-error.log* + +/src/config.js diff --git a/public/index.html b/public/index.html index 85ed71bd..9a67001c 100644 --- a/public/index.html +++ b/public/index.html @@ -1,7 +1,7 @@ - + @@ -40,4 +40,4 @@ --> - \ No newline at end of file + diff --git a/src/components/App.js b/src/components/App.js index 1e217bee..9894f50f 100644 --- a/src/components/App.js +++ b/src/components/App.js @@ -2,7 +2,7 @@ import React, { Component } from "react"; import CurrencyConverterContainer from "./CurrencyConverterContainer"; import CurrencyRatesTableContainer from "./CurrencyRatesTableContainer"; import JumbotronFluid from "./elements/JumbotronFluid"; - +import config from '../config' class App extends Component { constructor() { super(), @@ -13,9 +13,11 @@ class App extends Component { date: new Date().toISOString().slice(0, 10) }); } + + getRates = () => { fetch( - `http://api.fixer.io/${this.state.date}?base=${this.state.baseCurrency}` + `http://api.fixer.io/${this.state.date}?base=${this.state.baseCurrency}?{config.key}` ) .then(response => response.json()) .then(json => { @@ -60,6 +62,7 @@ class App extends Component { const { baseCurrency, rates, date } = this.state; const currenciesArray = Object.keys(rates); //console.log("RATES Passed", rates); + console.log("RATES Passed", config.key); return (
diff --git a/src/components/BaseCurrencyForm.js b/src/components/BaseCurrencyForm.js index 5a9e2cfd..3239e60e 100644 --- a/src/components/BaseCurrencyForm.js +++ b/src/components/BaseCurrencyForm.js @@ -3,40 +3,40 @@ import Select from "./elements/Select"; import Button from "./elements/Button"; const BaseCurrencyForm = props => { - const { - rates, - baseCurrency, - switch_currency, - setDate, - date, - currenciesArray - } = props; - return ( -
- -
-
- ); + const { + rates, + baseCurrency, + switch_currency, + setDate, + date, + currenciesArray + } = props; + return ( +
+ +
+
+ ); }; BaseCurrencyForm.defaultProps = { - type: "button", - color: "default", - children: "Submit" + type: "button", + color: "default", + children: "Submit" }; export default BaseCurrencyForm; diff --git a/src/components/ConverterBaseCurrencySelector.js b/src/components/ConverterBaseCurrencySelector.js index f7665ccc..85fa4058 100644 --- a/src/components/ConverterBaseCurrencySelector.js +++ b/src/components/ConverterBaseCurrencySelector.js @@ -1,25 +1,28 @@ import React from "react"; import Select from "./elements/Select"; +import PropTypes from "prop-types"; + const ConverterBaseCurrencySelector = ({ - selectCurrency, - converterBaseCurrency, - currenciesArray + selectCurrency, + converterBaseCurrency, + currenciesArray }) => { - //currenciesArray.unshift(converterBaseCurrency); - return ( - + ); }; -ConverterConvertedCurrencySelector.propTypes = { - convertedCurrency: PropTypes.string.isRequired, - selectCurrency: PropTypes.func.isRequired, - currenciesArray: PropTypes.array.isRequired +ConverterBaseCurrencySelector.propTypes = { + convertedCurrency: PropTypes.string.isRequired, + selectCurrency: PropTypes.func.isRequired, + currenciesArray: PropTypes.array.isRequired }; export default ConverterBaseCurrencySelector; + diff --git a/src/components/ConverterConvertedCurrencySelector.js b/src/components/ConverterConvertedCurrencySelector.js index b0de2582..05045ab4 100644 --- a/src/components/ConverterConvertedCurrencySelector.js +++ b/src/components/ConverterConvertedCurrencySelector.js @@ -3,26 +3,26 @@ import Select from "./elements/Select"; import PropTypes from "prop-types"; const ConverterConvertedCurrencySelector = ({ - selectCurrency, - convertedCurrency, - currenciesArray + selectCurrency, + convertedCurrency, + currenciesArray }) => { - //currenciesArray.unshift(convertedCurrency); - return ( - + ); }; ConverterConvertedCurrencySelector.propTypes = { - convertedCurrency: PropTypes.string.isRequired, - selectCurrency: PropTypes.func.isRequired, - currenciesArray: PropTypes.array.isRequired + convertedCurrency: PropTypes.string.isRequired, + selectCurrency: PropTypes.func.isRequired, + currenciesArray: PropTypes.array.isRequired }; export default ConverterConvertedCurrencySelector; diff --git a/src/components/CurrencyConverterOutput.js b/src/components/CurrencyConverterOutput.jsx similarity index 100% rename from src/components/CurrencyConverterOutput.js rename to src/components/CurrencyConverterOutput.jsx diff --git a/src/components/elements/Table.js b/src/components/elements/Table.js index dd8c00a4..41a3e4ad 100644 --- a/src/components/elements/Table.js +++ b/src/components/elements/Table.js @@ -2,28 +2,28 @@ import React from "react"; import Converter from "./Converter"; const Table = props => { - const { baseCurrency, rates } = props; - const currenciesArr = []; + const { baseCurrency, rates } = props; + const currenciesArr = []; - const currencies = Object.keys(rates).forEach(function(key, index) { - currenciesArr.push( - - {key} - {rates[key]} - {1 / rates[key]} - - ); - }); - return ( - - - - - - - {currenciesArr} -
CurrencyUnits per {baseCurrency}{baseCurrency} per Unit
- ); + const currencies = Object.keys(rates).forEach(function(key, index) { + currenciesArr.push( + + {key} + {rates[key]} + {1 / rates[key]} + + ); + }); + return ( + + + + + + + {currenciesArr} +
CurrencyUnits per {baseCurrency}{baseCurrency} per Unit
+ ); }; export default Table; diff --git a/src/index.css b/src/index.css index b554f4b6..f0a4785a 100644 --- a/src/index.css +++ b/src/index.css @@ -1,104 +1,104 @@ body { - margin: 0; - padding: 0; - font-family: sans-serif; + margin: 0; + padding: 0; + font-family: sans-serif; } .currency_table { - width: 90%; - margin: 2rem auto; - max-height: 15rem; - overflow: auto; - font-size: 1.2rem; + width: 90%; + margin: 2rem auto; + max-height: 15rem; + overflow: auto; + font-size: 1.2rem; } .currency_table * { - margin: 0 auto; + margin: 0 auto; } .currency_table th { - width: 1%; + width: 1%; } #ChooseBaseCurrency { - width: 90%; - text-align: center; + width: 90%; + text-align: center; } #ChooseBaseCurrency * { - width: 30%; - margin: 0.5rem 3rem; - display: inline-block; - font-size: 1.5rem; + width: 30%; + margin: 0.5rem 3rem; + display: inline-block; + font-size: 1.5rem; } @media (max-width: 865px) { - #ChooseBaseCurrency * { - width: 60%; - margin: 1rem 3rem; - display: inline-block; - font-size: 1.5rem; - } - .currency_table { - width: 92%; - margin: 1rem auto; - max-height: fit-content; - font-size: 1rem; - } + #ChooseBaseCurrency * { + width: 60%; + margin: 1rem 3rem; + display: inline-block; + font-size: 1.5rem; + } + .currency_table { + width: 92%; + margin: 1rem auto; + max-height: fit-content; + font-size: 1rem; + } } section h1 { - width: 50%; - margin: 5rem auto; - text-decoration: none; - background-color: #9fbcdf; - outline: 38px solid #9fbcdf; + width: 50%; + margin: 5rem auto; + text-decoration: none; + background-color: #9fbcdf; + outline: 38px solid #9fbcdf; } .converter_wrapper { - text-align: center; - margin-top: 3rem; + text-align: center; + margin-top: 3rem; } #currencyConverterForm { - outline: 1px solid #d9d8d8; - padding: 0.5rem; - margin-bottom: 8rem; + outline: 1px solid #d9d8d8; + padding: 0.5rem; + margin-bottom: 8rem; } #currencyConverterForm input, #currencyConverterForm select { - width: 8rem; - height: 2.5rem; - margin: 0.5rem 1.5rem; + width: 8rem; + height: 2.5rem; + margin: 0.5rem 1.5rem; } .converter_get_input, .outcome { - display: flex; - flex-wrap: wrap; - width: fit-content; - margin: 0.5rem auto; + display: flex; + flex-wrap: wrap; + width: fit-content; + margin: 0.5rem auto; } #converter_to { - font-family: sans-serif; - margin: -0.1rem 3rem; - font-size: 2rem; - font-style: italic; - font-weight: 500; + font-family: sans-serif; + margin: -0.1rem 3rem; + font-size: 2rem; + font-style: italic; + font-weight: 500; } .rate { - display: flex; - width: fit-content; - margin: 0.5rem auto; + display: flex; + width: fit-content; + margin: 0.5rem auto; } .rate p { - margin: 0 2rem; - font-size: 2rem; + margin: 0 2rem; + font-size: 2rem; } .outcome { - border: 2px solid #6ec2ba; - margin: 2rem auto; + border: 2px solid #6ec2ba; + margin: 2rem auto; } .outcome p { - width: 10rem; - font-size: 2rem; + width: 10rem; + font-size: 2rem; }