diff --git a/__tests__/shared/components/__snapshots__/Content.jsx.snap b/__tests__/shared/components/__snapshots__/Content.jsx.snap index aa78eb8e43..49dcc79e56 100644 --- a/__tests__/shared/components/__snapshots__/Content.jsx.snap +++ b/__tests__/shared/components/__snapshots__/Content.jsx.snap @@ -374,6 +374,19 @@ exports[`Matches shallow shapshot 1`] = ` . +
  • + + Tags + + - Demo/test of standard tags already available in the code, and customizable with help of + + react-css-themr + + . +
  • { test('click', () => { instance = TU.renderIntoDocument(()); - const tags = TU.findAllInRenderedTree(instance, item => - item && item.className && item.className.match('technology')); - expect(tags).toHaveLength(4); - TU.Simulate.click(tags[0]); + const tags = TU.scryRenderedComponentsWithType(instance, Tag); + const el = ReactDOM.findDOMNode(tags[0]); + expect(tags).toHaveLength(4); + TU.Simulate.click(el); }); test('click + tag', () => { instance = TU.renderIntoDocument(()); - const tags = TU.findAllInRenderedTree(instance, item => - item && item.className && item.className.match('technology')); - TU.Simulate.click(tags[0]); + const tags = TU.scryRenderedComponentsWithType(instance, Tag); + const el = ReactDOM.findDOMNode(tags[0]); + TU.Simulate.click(el); }); }); diff --git a/__tests__/shared/components/challenge-listing/Listing/Bucket.jsx b/__tests__/shared/components/challenge-listing/Listing/Bucket.jsx index 9749078637..3226e83c1f 100644 --- a/__tests__/shared/components/challenge-listing/Listing/Bucket.jsx +++ b/__tests__/shared/components/challenge-listing/Listing/Bucket.jsx @@ -1,10 +1,12 @@ import React from 'react'; +import ReactDOM from 'react-dom'; import _ from 'lodash'; import Renderer from 'react-test-renderer/shallow'; import TU from 'react-dom/test-utils'; import Bucket from 'components/challenge-listing/Listing/Bucket'; import reduxStoreFactory from 'redux-mock-store'; import { Provider } from 'react-redux'; +import { Tag } from 'components/tags'; const store = reduxStoreFactory()(); @@ -176,14 +178,13 @@ class Wrapper extends React.Component { const instance = TU.renderIntoDocument(()); test('setFilterState', () => { - const matches = TU.findAllInRenderedTree(instance, item => - item && item.className && item.className.match('technology')); + const matches = TU.scryRenderedComponentsWithType(instance, Tag); expect(matches).toHaveLength(3); - TU.Simulate.click(matches[0]); + TU.Simulate.click(ReactDOM.findDOMNode(matches[0])); expect(setFilterState).toHaveBeenCalledTimes(1); - TU.Simulate.click(matches[1]); + TU.Simulate.click(ReactDOM.findDOMNode(matches[1])); expect(setFilterState).toHaveBeenCalledTimes(2); - TU.Simulate.click(matches[2]); + TU.Simulate.click(ReactDOM.findDOMNode(matches[2])); expect(setFilterState).toHaveBeenCalledTimes(3); }); diff --git a/src/shared/components/Content/index.jsx b/src/shared/components/Content/index.jsx index a9703cde03..c5cbae6777 100644 --- a/src/shared/components/Content/index.jsx +++ b/src/shared/components/Content/index.jsx @@ -152,6 +152,11 @@ export default function Content() { load .svg assets with use of babel-plugin-inline-react-svg.
  • +
  • + Tags - Demo/test of standard + tags already available in the code, and customizable with help + of react-css-themr. +
  • Themr - Test/demo of react-css-themr. diff --git a/src/shared/components/buttons/index.jsx b/src/shared/components/buttons/index.jsx index 3cd612cf26..34b73fd061 100644 --- a/src/shared/components/buttons/index.jsx +++ b/src/shared/components/buttons/index.jsx @@ -123,4 +123,4 @@ export const PrimaryButton = export const SecondaryButton = themr('SecondaryButton', secondaryButton)(GenericButton); -export default undefined; + export default undefined; diff --git a/src/shared/components/challenge-detail/Header/ChallengeTags.jsx b/src/shared/components/challenge-detail/Header/ChallengeTags.jsx index 47c1574254..1e71189fb4 100644 --- a/src/shared/components/challenge-detail/Header/ChallengeTags.jsx +++ b/src/shared/components/challenge-detail/Header/ChallengeTags.jsx @@ -11,15 +11,13 @@ import PT from 'prop-types'; import _ from 'lodash'; import { Link } from 'utils/router'; -import './style.scss'; +import { Tag, EventTag, PrimaryTag } from 'components/tags'; export default function ChallengeTags(props) { const { subTrack, events, technPlatforms, - subTrackStyle, - eventStyle, setChallengeListingFilter, challengeSubtracksMap, } = props; @@ -33,34 +31,32 @@ export default function ChallengeTags(props) { }; return ( -
    +
    { subTrack && - setChallengeListingFilter({ subtracks: [subTrack] })} + {stylizedSubTrack(subTrack)} + onClick={() => setChallengeListingFilter({ subtracks: [subTrack] })} + >{stylizedSubTrack(subTrack)} } { events.map(event => ( - {event} + >{event} )) } { technPlatforms.map( tag => ( - setChallengeListingFilter({ tags: [tag] })} + tag && + {tag} + onClick={() => setChallengeListingFilter({ tags: [tag] })} + key={tag} + >{tag} ), ) } @@ -78,8 +74,6 @@ ChallengeTags.propTypes = { subTrack: PT.string, events: PT.arrayOf(PT.string), technPlatforms: PT.arrayOf(PT.string), - subTrackStyle: PT.string.isRequired, - eventStyle: PT.string.isRequired, setChallengeListingFilter: PT.func.isRequired, challengeSubtracksMap: PT.shape().isRequired, }; diff --git a/src/shared/components/challenge-detail/Header/index.jsx b/src/shared/components/challenge-detail/Header/index.jsx index 884ef7d121..d8a13530e5 100755 --- a/src/shared/components/challenge-detail/Header/index.jsx +++ b/src/shared/components/challenge-detail/Header/index.jsx @@ -66,9 +66,8 @@ export default function ChallengeHeader(props) { } const theme = themeFactory(trackLower); - - const subTrackStyle = `${trackLower}-accent-background`; - const eventStyle = `${trackLower}-accent-color`; + const stylizedSubTrack = (subTrack || '').replace('_', ' ') + .replace(/\w\S*/g, txt => _.capitalize(txt)); const eventNames = (events || []).map((event => (event.eventName || '').toUpperCase())); const miscTags = _.union((technologies || '').split(', '), platforms.split(', ')); @@ -184,8 +183,6 @@ export default function ChallengeHeader(props) { challengeSubtracksMap={challengeSubtracksMap} events={eventNames} technPlatforms={miscTags} - subTrackStyle={subTrackStyle} - eventStyle={eventStyle} setChallengeListingFilter={setChallengeListingFilter} />
    diff --git a/src/shared/components/challenge-detail/Header/style.scss b/src/shared/components/challenge-detail/Header/style.scss index f784517963..5ef8e6c0ee 100644 --- a/src/shared/components/challenge-detail/Header/style.scss +++ b/src/shared/components/challenge-detail/Header/style.scss @@ -124,39 +124,17 @@ } } - .tag-holder { - .tag-common { - border-radius: 3px; - font-family: roboto; - font-size: 10px; - line-height: 20px; - margin: 5px 5px 0 0; - display: inline-block; - text-align: center; - padding: 0 5px; - font-weight: 700; - color: $tc-white; - background-color: $tc-light-blue-10; - } - - .design-accent-background { - background-color: $tc-light-blue; - } - - .design-accent-color { - background-color: $tc-light-blue; - } - - @include develop-accent-bg; - @include datasci-accent-bg; - @include develop-accent-clr; - @include datasci-accent-clr; - - .misc-tag { - color: $tc-gray-80; - background-color: $tc-gray-neutral-dark; - cursor: pointer; - } + @include design-accent-bg; + @include develop-accent-bg; + @include datasci-accent-bg; + @include design-accent-clr; + @include develop-accent-clr; + @include datasci-accent-clr; + + .miscTag { + color: $tc-gray-80; + background-color: $tc-gray-neutral-dark; + cursor: pointer; } .prizes-ops-container { @@ -260,10 +238,7 @@ font-weight: 500; } - .design-accent-color { - color: $tc-light-blue; - } - + @include design-accent-clr; @include develop-accent-clr; @include datasci-accent-clr; } diff --git a/src/shared/components/challenge-detail/themeFactory.js b/src/shared/components/challenge-detail/themeFactory.js index 2a65f7c427..d54f19e4e3 100644 --- a/src/shared/components/challenge-detail/themeFactory.js +++ b/src/shared/components/challenge-detail/themeFactory.js @@ -10,9 +10,10 @@ import { COMPETITION_TRACKS } from 'utils/tc'; -// import primaryDesignButtonStyle from '../buttons/primaryDesign.scss'; -// import primaryDevelopButtonStyle from '../buttons/primaryDevelop.scss'; -// import primaryDataScienceButtonStyle from '../buttons/primaryDataScience.scss'; + import primaryDevelopTagStyle from '../tags/primaryDevelop.scss'; + import primaryDataScienceTagStyle from '../tags/primaryDataScience.scss'; + import eventDevelopTagStyle from '../tags/eventDevelop.scss'; + import eventDataScienceTagStyle from '../tags/eventDataScience.scss'; export default function factory(track) { /* Currently track value can come either from Topcoder API v2, where it is @@ -21,15 +22,17 @@ export default function factory(track) { switch (track.toLowerCase()) { case COMPETITION_TRACKS.DATA_SCIENCE: return { - // PrimaryButton: primaryDataScienceButtonStyle, + PrimaryTag: primaryDataScienceTagStyle, + EventTag: eventDataScienceTagStyle, }; case COMPETITION_TRACKS.DESIGN: return { - // PrimaryButton: primaryDesignButtonStyle, + }; case COMPETITION_TRACKS.DEVELOP: return { - // PrimaryButton: primaryDevelopButtonStyle, + PrimaryTag: primaryDevelopTagStyle, + EventTag: eventDevelopTagStyle, }; default: throw new Error('Wrong competition track value!'); diff --git a/src/shared/components/challenge-listing/ChallengeCard/index.jsx b/src/shared/components/challenge-listing/ChallengeCard/index.jsx index 40c2633cd7..2acf0b7875 100644 --- a/src/shared/components/challenge-listing/ChallengeCard/index.jsx +++ b/src/shared/components/challenge-listing/ChallengeCard/index.jsx @@ -11,6 +11,7 @@ import Prize from './Prize'; import ChallengeStatus from './Status'; import TrackAbbreviationTooltip from '../Tooltips/TrackAbbreviationTooltip'; import './style.scss'; +import { Tag } from 'components/tags'; export const PRIZE_MODE = { HIDDEN: 'hidden', @@ -228,15 +229,11 @@ class Tags extends React.Component { technologyList.push(lastItem); } return technologyList.map(c => ( - this.onClick(c.trim())} + key={c} role="button" - tabIndex={0} - >{c} + >{c} )); } return ''; diff --git a/src/shared/components/examples/Tags/index.jsx b/src/shared/components/examples/Tags/index.jsx new file mode 100644 index 0000000000..989d0e40fb --- /dev/null +++ b/src/shared/components/examples/Tags/index.jsx @@ -0,0 +1,83 @@ +import React from 'react'; +import { + Tag, + PrimaryTag, + EventTag +} from 'components/tags'; +import { ThemeProvider } from 'react-css-themr'; + +import primaryDataScienceTagStyle from '../../tags/primaryDataScience.scss'; +import primaryDevelopTagStyle from '../../tags/primaryDevelop.scss'; +import eventDevelopTagStyle from '../../tags/eventDevelop.scss'; +import eventDataScienceTagStyle from '../../tags/eventDataScience.scss'; + +import style from './style.scss'; + +export default function Tags() { + return ( +
    +

    Tags

    +

    + All tags in this page are instances of the generic tag, + implemented in /src/components/tags and wrapped + into different style themes with help + of react-css-themr. +

    + +

    Default Tag

    + Tag + Link Tag + +

    Primary Tag

    + +

    Default — design color scheme:

    + Tag + Link Tag + +

    Develop color scheme (underlying source code also + demonstrates the proper context theming in action):

    + + +
    + Tag + Link Tag +
    +
    + +

    Data science color scheme:

    + +
    + Tag + Link Tag +
    +
    + +

    Event Tag

    +

    Default — design color scheme:

    + Tag + Link Tag +

    Develop color scheme:

    + +
    + Tag + Link Tag +
    +
    +

    Data Science color scheme:

    + +
    + Tag + Link Tag +
    +
    +
    + ); +} diff --git a/src/shared/components/examples/Tags/style.scss b/src/shared/components/examples/Tags/style.scss new file mode 100644 index 0000000000..ba581c0fc4 --- /dev/null +++ b/src/shared/components/examples/Tags/style.scss @@ -0,0 +1,43 @@ +@import "~styles/tc-styles"; + +.page { + @include roboto-light; + + line-height: 150%; + margin: auto; + max-width: $screen-lg; + padding: 24px; + + h1 { + margin: 0 0 18px; + } + + h3 { + margin: 24px 0 6px; + } + + code { + background: whitesmoke; + padding: 2px 4px; + } + + em { + font-style: italic; + } + + p { + margin: $base-unit 0; + } +} + +.btnXS { + @include btn-xs; +} + +.btnSM { + @include btn-sm; +} + +.btnLG { + @include btn-lg; +} diff --git a/src/shared/components/tags/default.scss b/src/shared/components/tags/default.scss new file mode 100644 index 0000000000..8ef3a7c399 --- /dev/null +++ b/src/shared/components/tags/default.scss @@ -0,0 +1,35 @@ +/** + * Challenge tag button, default style with white text on light blue background. + */ + @import "~styles/tc-styles"; + +@mixin feedback { + &:active, + &:focus, + &:hover { + color: $tc-gray-80; + background-color: $tc-dark-blue-30; + } + &:visited { + color: $tc-gray-80; + } +} + +div, span { + .tag, a.tag { + display: inline-block; + text-align: center; + padding: 0 7px; + line-height: 20px; + background-color: $tc-gray-neutral-dark; + font-size: 11px; + font-family: Roboto; + font-weight: 500; + color: $tc-gray-80; + margin-right: 5px; + border-radius: 4px; + margin-bottom: 2px; + cursor: pointer; + @include feedback; + } +} \ No newline at end of file diff --git a/src/shared/components/tags/eventDataScience.scss b/src/shared/components/tags/eventDataScience.scss new file mode 100644 index 0000000000..58f29231f2 --- /dev/null +++ b/src/shared/components/tags/eventDataScience.scss @@ -0,0 +1,25 @@ +/** + * Event tag, colored with colors of data science track (orange). + */ + + @import "~styles/tc-styles"; + + @mixin feedback { + &:active, + &:focus, + &:hover { + color: $tc-orange; + background-color: $tc-light-blue-10; + } + &:visited { + color: $tc-orange; + } + } + +div, span { + .tag, a.tag { + color: $tc-orange; + background-color: $tc-light-blue-10; + @include feedback; + } +} \ No newline at end of file diff --git a/src/shared/components/tags/eventDesign.scss b/src/shared/components/tags/eventDesign.scss new file mode 100644 index 0000000000..942adfc6b3 --- /dev/null +++ b/src/shared/components/tags/eventDesign.scss @@ -0,0 +1,31 @@ +/** + * Event tag, colored with colors of design track (blue). + */ + + @import "./default"; + + + @mixin feedback { + &:active, + &:focus, + &:hover { + color: $tc-dark-blue-90; + background-color: $tc-light-blue-10; + } + &:visited { + color: $tc-dark-blue-90; + } + } + +div, span { + .tag, a.tag { + border-radius: 3px; + font-size: 10px; + margin: 5px 5px 0 0; + padding: 0 5px; + font-weight: 700; + color: $tc-dark-blue-90; + background-color: $tc-light-blue-10; + @include feedback; + } +} \ No newline at end of file diff --git a/src/shared/components/tags/eventDevelop.scss b/src/shared/components/tags/eventDevelop.scss new file mode 100644 index 0000000000..b49d35528a --- /dev/null +++ b/src/shared/components/tags/eventDevelop.scss @@ -0,0 +1,24 @@ +/** + * Event tag, colored with colors of develop track (green). + */ + @import "~styles/tc-styles"; + + @mixin feedback { + &:active, + &:focus, + &:hover { + color: $tc-green; + background-color: $tc-light-blue-10; + } + &:visited { + color: $tc-green; + } + } + +div, span { + .tag, a.tag { + color: $tc-green; + background-color: $tc-light-blue-10; + @include feedback; + } +} \ No newline at end of file diff --git a/src/shared/components/tags/index.jsx b/src/shared/components/tags/index.jsx new file mode 100644 index 0000000000..c2e74dcf18 --- /dev/null +++ b/src/shared/components/tags/index.jsx @@ -0,0 +1,80 @@ +import PT from 'prop-types'; +import React from 'react'; +import { themr } from 'react-css-themr'; +import { Link } from 'utils/router'; + +import defaultTag from './default.scss'; +import primaryDesignTag from './primaryDesign.scss'; +import eventDesignTag from './eventDesign.scss'; + +/* Generic button, not wrapped by themr, but accepting theme property. + * In most cases you will want to use some of the themable exports below + * instead. */ +export function GenericTag({ + children, + enforceA, + onClick, + openNewTab, + replace, + role, + tabIndex, + theme, + to, +}) { + if (to) { + return ( + {children} + ); + } + return ( + {children} + ); +} + +GenericTag.defaultProps = { + children: null, + enforceA: false, + onClick: null, + openNewTab: false, + replace: false, + role: "button", + tabIndex: 0, + to: null, +}; + +GenericTag.propTypes = { + children: PT.node, + enforceA: PT.bool, + onClick: PT.func, + openNewTab: PT.bool, + replace: PT.bool, + role: PT.string, + tabIndex: PT.number, + theme: PT.shape({ + tag: PT.string.isRequired, + }).isRequired, + to: PT.oneOfType([PT.object, PT.string]), +}; + +export const Tag = + themr('Tag', defaultTag)(GenericTag); + +export const PrimaryTag = + themr('PrimaryTag', primaryDesignTag)(GenericTag); + +export const EventTag = + themr('EventTag', eventDesignTag)(GenericTag); + + export default undefined; diff --git a/src/shared/components/tags/primaryDataScience.scss b/src/shared/components/tags/primaryDataScience.scss new file mode 100644 index 0000000000..953b82bb60 --- /dev/null +++ b/src/shared/components/tags/primaryDataScience.scss @@ -0,0 +1,25 @@ +/** + * Primary tag, colored with colors of data science track (orange). + */ + + @import "~styles/tc-styles"; + + @mixin feedback { + &:active, + &:focus, + &:hover { + color: $tc-white; + background-color: $tc-orange; + } + &:visited { + color: $tc-white; + } + } + +div, span { + .tag, a.tag { + color: $tc-white; + background-color: $tc-orange; + @include feedback; + } +} \ No newline at end of file diff --git a/src/shared/components/tags/primaryDesign.scss b/src/shared/components/tags/primaryDesign.scss new file mode 100644 index 0000000000..eeca88ba33 --- /dev/null +++ b/src/shared/components/tags/primaryDesign.scss @@ -0,0 +1,31 @@ +/** + * Primary tag, colored with colors of design track (blue). + */ + + @import "./default"; + + + @mixin feedback { + &:active, + &:focus, + &:hover { + color: $tc-white; + background-color: $tc-dark-blue-90; + } + &:visited { + color: $tc-white; + } + } + +div, span { + .tag, a.tag { + border-radius: 3px; + font-size: 10px; + margin: 5px 5px 0 0; + padding: 0 5px; + font-weight: 700; + color: $tc-white; + background-color: $tc-dark-blue-90; + @include feedback; + } +} \ No newline at end of file diff --git a/src/shared/components/tags/primaryDevelop.scss b/src/shared/components/tags/primaryDevelop.scss new file mode 100644 index 0000000000..9fc0ee8857 --- /dev/null +++ b/src/shared/components/tags/primaryDevelop.scss @@ -0,0 +1,25 @@ +/** + * Primary tag, colored with colors of develop track (green). + */ + + @import "~styles/tc-styles"; + + @mixin feedback { + &:active, + &:focus, + &:hover { + color: $tc-white; + background-color: $tc-green; + } + &:visited { + color: $tc-white; + } + } + +div, span { + .tag, a.tag { + color: $tc-white; + background-color: $tc-green; + @include feedback; + } +} \ No newline at end of file diff --git a/src/shared/routes/Examples/Examples.jsx b/src/shared/routes/Examples/Examples.jsx index 2c6fc79a5e..2067294cf8 100644 --- a/src/shared/routes/Examples/Examples.jsx +++ b/src/shared/routes/Examples/Examples.jsx @@ -16,6 +16,7 @@ import { Route, } from 'react-router-dom'; import SvgLoading from 'components/examples/SvgLoading'; +import Tags from 'components/examples/Tags'; import Themr from 'components/examples/Themr'; import { requireWeak, resolveWeak, SplitRoute } from 'utils/router'; @@ -48,6 +49,7 @@ export default function Examples(props) { + diff --git a/src/shared/services/.exchange-rates.cache b/src/shared/services/.exchange-rates.cache index 087a18a0fb..95c6630835 100644 --- a/src/shared/services/.exchange-rates.cache +++ b/src/shared/services/.exchange-rates.cache @@ -1 +1,2 @@ -{"disclaimer":"Usage subject to terms: https://openexchangerates.org/terms","license":"https://openexchangerates.org/license","timestamp":1504137600,"base":"USD","rates":{"AED":3.673097,"AFN":68.445423,"ALL":111.791078,"AMD":480.27149,"ANG":1.78843,"AOA":165.9205,"ARS":17.395,"AUD":1.264894,"AWG":1.794996,"AZN":1.7,"BAM":1.644699,"BBD":2,"BDT":81.689034,"BGN":1.64397,"BHD":0.377055,"BIF":1749.75,"BMD":1,"BND":1.356545,"BOB":7.008005,"BRL":3.1603,"BSD":1,"BTC":0.00021700956,"BTN":63.98413,"BWP":10.164186,"BYN":1.941205,"BZD":2.025258,"CAD":1.263078,"CDF":1550.740385,"CHF":0.963759,"CLF":0.02349,"CLP":631.9,"CNH":6.599327,"CNY":6.595577,"COP":2953.5,"CRC":579.374449,"CUC":1,"CUP":25.5,"CVE":92.8,"CZK":21.92111,"DJF":178.77,"DKK":6.256053,"DOP":47.279238,"DZD":110.9295,"EGP":17.643,"ERN":15.335471,"ETB":23.319528,"EUR":0.840993,"FJD":2.034645,"FKP":0.774009,"GBP":0.774009,"GEL":2.4245,"GGP":0.774009,"GHS":4.456015,"GIP":0.774009,"GMD":46.15,"GNF":8930.05,"GTQ":7.320704,"GYD":207.972754,"HKD":7.824991,"HNL":23.509381,"HRK":6.2329,"HTG":63.506176,"HUF":257.132505,"IDR":13345.175458,"ILS":3.58885,"IMP":0.774009,"INR":63.9874,"IQD":1172.5,"IRR":33062.267348,"ISK":105.747443,"JEP":0.774009,"JMD":128.693699,"JOD":0.709001,"JPY":110.4721,"KES":103.18,"KGS":68.664403,"KHR":4075.766667,"KMF":414.090225,"KPW":900,"KRW":1124.28,"KWD":0.301448,"KYD":0.837333,"KZT":336.825303,"LAK":8328.65,"LBP":1509.062443,"LKR":153.581733,"LRD":115.030245,"LSL":13.085258,"LYD":1.368959,"MAD":9.370738,"MDL":17.864359,"MGA":2982.444875,"MKD":51.78,"MMK":1369.51006,"MNT":2428.158099,"MOP":8.098407,"MRO":366.89879,"MUR":32.6185,"MVR":15.450233,"MWK":725.046611,"MXN":17.74,"MYR":4.2715,"MZN":61.160857,"NAD":13.085258,"NGN":355,"NIO":29.996418,"NOK":7.80381,"NPR":102.833791,"NZD":1.388156,"OMR":0.384992,"PAB":1,"PEN":3.240393,"PGK":3.199435,"PHP":51.149,"PKR":105.725129,"PLN":3.57795,"PYG":5696.477124,"QAR":3.685006,"RON":3.863137,"RSD":100.15515,"RUB":58.4901,"RWF":831,"SAR":3.7503,"SBD":7.797375,"SCR":13.631694,"SDG":6.708373,"SEK":7.975026,"SGD":1.358101,"SHP":0.774009,"SLL":7550.184032,"SOS":580.38334,"SRD":7.438,"SSP":124.9444,"STD":20528.502691,"SVC":8.791576,"SYP":515,"SZL":13.096402,"THB":33.2155,"TJS":8.856445,"TMT":3.499986,"TND":2.434089,"TOP":2.193576,"TRY":3.456008,"TTD":6.757558,"TWD":30.151,"TZS":2241.25,"UAH":25.716003,"UGX":3627.308069,"USD":1,"UYU":28.773276,"UZS":4201.65,"VEF":10.05845,"VND":22722.55232,"VUV":105.013288,"WST":2.497571,"XAF":551.655496,"XAG":0.05750432,"XAU":0.00076489,"XCD":2.70255,"XDR":0.7051,"XOF":551.655496,"XPD":0.0010724,"XPF":100.357205,"XPT":0.0010091,"YER":250.35,"ZAR":13.01652,"ZMW":9.077975,"ZWL":322.355011}} \ No newline at end of file + +{"disclaimer":"Usage subject to terms: https://openexchangerates.org/terms","license":"https://openexchangerates.org/license","timestamp":1504152000,"base":"USD","rates":{"AED":3.673097,"AFN":68.753,"ALL":111.791078,"AMD":480.79,"ANG":1.788544,"AOA":165.9205,"ARS":17.397,"AUD":1.265096,"AWG":1.794996,"AZN":1.7,"BAM":1.644699,"BBD":2,"BDT":81.6885,"BGN":1.64768,"BHD":0.376988,"BIF":1749.85,"BMD":1,"BND":1.356545,"BOB":7.008309,"BRL":3.1604,"BSD":1,"BTC":0.000214876709,"BTN":64.002922,"BWP":10.165203,"BYN":1.941418,"BZD":2.025349,"CAD":1.26401,"CDF":1550.740385,"CHF":0.964134,"CLF":0.02349,"CLP":631.9,"CNH":6.603155,"CNY":6.596007,"COP":2953.5,"CRC":578.835,"CUC":1,"CUP":25.5,"CVE":92.8,"CZK":21.953782,"DJF":178.77,"DKK":6.264427,"DOP":47.2815,"DZD":110.734,"EGP":17.638,"ERN":15.338604,"ETB":23.321,"EUR":0.842132,"FJD":2.034645,"FKP":0.774439,"GBP":0.774439,"GEL":2.426725,"GGP":0.774439,"GHS":4.456189,"GIP":0.774439,"GMD":46.15,"GNF":8930.7,"GTQ":7.321298,"GYD":207.972754,"HKD":7.825497,"HNL":23.5105,"HRK":6.2428,"HTG":63.512,"HUF":257.473748,"IDR":13350.737506,"ILS":3.589475,"IMP":0.774439,"INR":64.0225,"IQD":1172.6,"IRR":33164.5,"ISK":105.87,"JEP":0.774439,"JMD":128.68,"JOD":0.709001,"JPY":110.54041071,"KES":103.175,"KGS":68.675501,"KHR":4068.5,"KMF":414.090225,"KPW":900,"KRW":1125.55,"KWD":0.301434,"KYD":0.837427,"KZT":336.955,"LAK":8329.15,"LBP":1513.7,"LKR":153.635,"LRD":115.030245,"LSL":13.086864,"LYD":1.369091,"MAD":9.38025,"MDL":17.8955,"MGA":2979.25,"MKD":51.87,"MMK":1369,"MNT":2428.467354,"MOP":8.09906,"MRO":366.735,"MUR":32.6115,"MVR":15.450233,"MWK":725.046611,"MXN":17.73081,"MYR":4.2715,"MZN":61.160857,"NAD":13.087114,"NGN":361.25,"NIO":29.999232,"NOK":7.810398,"NPR":102.83,"NZD":1.39479,"OMR":0.384987,"PAB":1,"PEN":3.240393,"PGK":3.199713,"PHP":51.157,"PKR":105.735,"PLN":3.582625,"PYG":5674.55,"QAR":3.685006,"RON":3.868227,"RSD":100.2925,"RUB":58.4916,"RWF":831,"SAR":3.75015,"SBD":7.812222,"SCR":13.631558,"SDG":6.708748,"SEK":7.986789,"SGD":1.35839,"SHP":0.774439,"SLL":7524.999807,"SOS":581.27,"SRD":7.438,"SSP":124.9444,"STD":20583.157597,"SVC":8.79201,"SYP":515,"SZL":13.09776,"THB":33.22075,"TJS":8.857112,"TMT":3.499986,"TND":2.435798,"TOP":2.19132,"TRY":3.45735,"TTD":6.758012,"TWD":30.1505,"TZS":2241.25,"UAH":25.718,"UGX":3617.15,"USD":1,"UYU":28.764997,"UZS":4202.05,"VEF":10.05845,"VND":22752.373857,"VUV":105.078218,"WST":2.511557,"XAF":552.402553,"XAG":0.05764137,"XAU":0.00076742,"XCD":2.70255,"XDR":0.7051,"XOF":552.402553,"XPD":0.00107336,"XPF":100.49311,"XPT":0.00101536,"YER":250.35,"ZAR":13.032813,"ZMW":9.078587,"ZWL":322.355011}}