From fc82c866fb3b372140241b822a3b9627f79d3be2 Mon Sep 17 00:00:00 2001 From: diminator Date: Mon, 17 Aug 2015 20:52:36 +0200 Subject: [PATCH] cyland refactor whitelabel + cyland app --- .../accordion_list_item_piece.js | 25 +--- .../ascribe_detail/further_details.js | 5 +- .../further_details_fileuploader.js | 6 +- .../ascribe_detail/piece_container.js | 2 +- .../accordion_list_item_prize.js | 2 +- .../prize/constants/prize_api_urls.js | 2 +- js/components/whitelabel/prize/prize_app.js | 2 +- .../cyland_accordion_list_item.js | 93 ++++++++++++ .../ascribe_buttons/cyland_submit_button.js | 54 +++++++ .../ascribe_detail/cyland_piece_container.js | 137 ++++++++++++++++++ .../cyland_additional_data_form.js | 18 +-- .../components/cyland/cyland_piece_list.js | 42 ++++++ .../cyland/cyland_register_piece.js | 14 +- .../wallet/constants/wallet_api_urls.js | 12 +- .../constants/wallet_application_constants.js | 2 +- js/components/whitelabel/wallet/wallet_app.js | 2 +- .../whitelabel/wallet/wallet_routes.js | 7 +- js/constants/application_constants.js | 16 +- 18 files changed, 381 insertions(+), 60 deletions(-) create mode 100644 js/components/whitelabel/wallet/components/cyland/ascribe_accordion_list/cyland_accordion_list_item.js create mode 100644 js/components/whitelabel/wallet/components/cyland/ascribe_buttons/cyland_submit_button.js create mode 100644 js/components/whitelabel/wallet/components/cyland/ascribe_detail/cyland_piece_container.js rename js/components/whitelabel/wallet/components/{ => cyland}/ascribe_forms/cyland_additional_data_form.js (85%) create mode 100644 js/components/whitelabel/wallet/components/cyland/cyland_piece_list.js diff --git a/js/components/ascribe_accordion_list/accordion_list_item_piece.js b/js/components/ascribe_accordion_list/accordion_list_item_piece.js index e1271b0a..b7e621b8 100644 --- a/js/components/ascribe_accordion_list/accordion_list_item_piece.js +++ b/js/components/ascribe_accordion_list/accordion_list_item_piece.js @@ -13,6 +13,7 @@ let Link = Router.Link; let AccordionListItemPiece = React.createClass({ propTypes: { className: React.PropTypes.string, + artistName: React.PropTypes.string, piece: React.PropTypes.object, children: React.PropTypes.oneOfType([ React.PropTypes.arrayOf(React.PropTypes.element), @@ -26,24 +27,12 @@ let AccordionListItemPiece = React.createClass({ mixins: [Router.Navigation], getLinkData(){ - let linkData; - - if (this.props.piece.num_editions < 1 || !this.props.piece.first_edition) { - linkData = { - to: 'piece', - params: { - pieceId: this.props.piece.id - } - }; - } else { - linkData = { - to: 'edition', - params: { - editionId: this.props.piece.first_edition.bitcoin_id - } - }; - } - return linkData; + return { + to: 'piece', + params: { + pieceId: this.props.piece.id + } + }; }, render() { diff --git a/js/components/ascribe_detail/further_details.js b/js/components/ascribe_detail/further_details.js index e8bf5d3b..57c6ebe1 100644 --- a/js/components/ascribe_detail/further_details.js +++ b/js/components/ascribe_detail/further_details.js @@ -20,7 +20,7 @@ let FurtherDetails = React.createClass({ editable: React.PropTypes.bool, pieceId: React.PropTypes.number, extraData: React.PropTypes.object, - otherData: React.PropTypes.object, + otherData: React.PropTypes.arrayOf(React.PropTypes.object), handleSuccess: React.PropTypes.func }, @@ -91,7 +91,8 @@ let FurtherDetails = React.createClass({ isReadyForFormSubmission={this.isReadyForFormSubmission} editable={this.props.editable} pieceId={this.props.pieceId} - otherData={this.props.otherData}/> + otherData={this.props.otherData} + multiple={true}/> diff --git a/js/components/ascribe_detail/further_details_fileuploader.js b/js/components/ascribe_detail/further_details_fileuploader.js index 5d9cd5fd..7c5525fd 100644 --- a/js/components/ascribe_detail/further_details_fileuploader.js +++ b/js/components/ascribe_detail/further_details_fileuploader.js @@ -14,7 +14,7 @@ import { getCookie } from '../../utils/fetch_api_utils'; let FurtherDetailsFileuploader = React.createClass({ propTypes: { pieceId: React.PropTypes.number, - otherData: React.PropTypes.object, + otherData: React.PropTypes.arrayOf(React.PropTypes.object), setIsUploadReady: React.PropTypes.func, submitKey: React.PropTypes.func, isReadyForFormSubmission: React.PropTypes.func, @@ -37,6 +37,8 @@ let FurtherDetailsFileuploader = React.createClass({ if (!this.props.editable && !this.props.otherData){ return null; } + let otherDataIds = this.props.otherData ? this.props.otherData.map((data)=>{return data.id; }).join() : null; + return ( @@ -63,7 +65,7 @@ let FurtherDetailsFileuploader = React.createClass({ 'X-CSRFToken': getCookie(AppConstants.csrftoken) }, params: { - 'pk': this.props.otherData ? this.props.otherData.id : null + 'pk': otherDataIds }, cors: { expected: true, diff --git a/js/components/ascribe_detail/piece_container.js b/js/components/ascribe_detail/piece_container.js index 2b607516..7380ada7 100644 --- a/js/components/ascribe_detail/piece_container.js +++ b/js/components/ascribe_detail/piece_container.js @@ -148,7 +148,7 @@ let PieceContainer = React.createClass({ loadPiece={this.loadPiece} header={
-
+

{this.state.piece.title}

diff --git a/js/components/whitelabel/prize/components/ascribe_accordion_list/accordion_list_item_prize.js b/js/components/whitelabel/prize/components/ascribe_accordion_list/accordion_list_item_prize.js index 73c82ca4..bf6301f0 100644 --- a/js/components/whitelabel/prize/components/ascribe_accordion_list/accordion_list_item_prize.js +++ b/js/components/whitelabel/prize/components/ascribe_accordion_list/accordion_list_item_prize.js @@ -98,7 +98,7 @@ let AccordionListItemPrize = React.createClass({
+ aclName="acl_submit"> +
{header}
diff --git a/js/components/whitelabel/wallet/components/cyland/ascribe_accordion_list/cyland_accordion_list_item.js b/js/components/whitelabel/wallet/components/cyland/ascribe_accordion_list/cyland_accordion_list_item.js new file mode 100644 index 00000000..c523739d --- /dev/null +++ b/js/components/whitelabel/wallet/components/cyland/ascribe_accordion_list/cyland_accordion_list_item.js @@ -0,0 +1,93 @@ +'use strict'; + +import React from 'react'; +import Router from 'react-router'; + +import AccordionListItemPiece from '../../../../../ascribe_accordion_list/accordion_list_item_piece'; + +import PieceListActions from '../../../../../../actions/piece_list_actions'; +import PieceListStore from '../../../../../../stores/piece_list_store'; + +import UserStore from '../../../../../../stores/user_store'; + +import GlobalNotificationModel from '../../../../../../models/global_notification_model'; +import GlobalNotificationActions from '../../../../../../actions/global_notification_actions'; + +import CylandSubmitButton from '../ascribe_buttons/cyland_submit_button'; +import AclProxy from '../../../../../acl_proxy'; + +import { getLangText } from '../../../../../../utils/lang_utils'; +import { mergeOptions } from '../../../../../../utils/general_utils'; + + +let CylandAccordionListItem = React.createClass({ + propTypes: { + className: React.PropTypes.string, + content: React.PropTypes.object, + children: React.PropTypes.oneOfType([ + React.PropTypes.arrayOf(React.PropTypes.element), + React.PropTypes.element + ]) + }, + + getInitialState() { + return mergeOptions( + PieceListStore.getState(), + UserStore.getState() + ); + }, + + componentDidMount() { + PieceListStore.listen(this.onChange); + UserStore.listen(this.onChange); + }, + + componentWillUnmount() { + PieceListStore.unlisten(this.onChange); + UserStore.unlisten(this.onChange); + }, + + onChange(state) { + this.setState(state); + }, + + handleSubmitSuccess(response) { + PieceListActions.fetchPieceList(this.state.page, this.state.pageSize, this.state.search, + this.state.orderBy, this.state.orderAsc, this.state.filterBy); + + let notification = new GlobalNotificationModel(response.notification, 'success', 10000); + GlobalNotificationActions.appendGlobalNotification(notification); + }, + + getSubmitButtons() { + return ( +
+ + + +
+ ); + }, + + render() { + return ( + + {this.props.content.date_created.split('-')[0]} +
} + buttons={this.getSubmitButtons()}> + {this.props.children} + + ); + } +}); + +export default CylandAccordionListItem; diff --git a/js/components/whitelabel/wallet/components/cyland/ascribe_buttons/cyland_submit_button.js b/js/components/whitelabel/wallet/components/cyland/ascribe_buttons/cyland_submit_button.js new file mode 100644 index 00000000..6e2246f8 --- /dev/null +++ b/js/components/whitelabel/wallet/components/cyland/ascribe_buttons/cyland_submit_button.js @@ -0,0 +1,54 @@ +'use strict'; + +import React from 'react'; +import classNames from 'classnames'; + +import ModalWrapper from '../../../../../ascribe_modal/modal_wrapper'; +import PieceSubmitToPrizeForm from '../../../../../ascribe_forms/form_submit_to_prize'; + +import { getLangText } from '../../../../../../utils/lang_utils'; + +let SubmitToPrizeButton = React.createClass({ + propTypes: { + className: React.PropTypes.string, + handleSuccess: React.PropTypes.func, + piece: React.PropTypes.object.isRequired + }, + + getSubmitButton() { + if (this.props.piece.prize) { + return ( + + ); + } + else { + return ( + + ); + } + }, + + render() { + return ( + + + + + ); + } +}); + +export default SubmitToPrizeButton; \ No newline at end of file diff --git a/js/components/whitelabel/wallet/components/cyland/ascribe_detail/cyland_piece_container.js b/js/components/whitelabel/wallet/components/cyland/ascribe_detail/cyland_piece_container.js new file mode 100644 index 00000000..d22d8638 --- /dev/null +++ b/js/components/whitelabel/wallet/components/cyland/ascribe_detail/cyland_piece_container.js @@ -0,0 +1,137 @@ +'use strict'; + +import React from 'react'; + +import PieceActions from '../../../../../../actions/piece_actions'; +import PieceStore from '../../../../../../stores/piece_store'; + +import UserStore from '../../../../../../stores/user_store'; + +import Piece from '../../../../../../components/ascribe_detail/piece'; + +import AppConstants from '../../../../../../constants/application_constants'; + +import Form from '../../../../../../components/ascribe_forms/form'; +import Property from '../../../../../../components/ascribe_forms/property'; +import InputTextAreaToggable from '../../../../../../components/ascribe_forms/input_textarea_toggable'; +import CollapsibleParagraph from '../../../../../../components/ascribe_collapsible/collapsible_paragraph'; + +import FurtherDetailsFileuploader from '../../../../../ascribe_detail/further_details_fileuploader'; +import DetailProperty from '../../../../../ascribe_detail/detail_property'; + +import { mergeOptions } from '../../../../../../utils/general_utils'; +import { getLangText } from '../../../../../../utils/lang_utils'; + +/** + * This is the component that implements resource/data specific functionality + */ +let CylandPieceContainer = React.createClass({ + getInitialState() { + return mergeOptions( + PieceStore.getState(), + UserStore.getState() + ); + }, + + componentDidMount() { + PieceStore.listen(this.onChange); + PieceActions.fetchOne(this.props.params.pieceId); + UserStore.listen(this.onChange); + }, + + componentWillUnmount() { + // Every time we're leaving the piece detail page, + // just reset the piece that is saved in the piece store + // as it will otherwise display wrong/old data once the user loads + // the piece detail a second time + PieceActions.updatePiece({}); + PieceStore.unlisten(this.onChange); + UserStore.unlisten(this.onChange); + }, + + componentWillReceiveProps(nextProps) { + if(this.props.params.pieceId !== nextProps.params.pieceId) { + PieceActions.updatePiece({}); + PieceActions.fetchOne(nextProps.params.pieceId); + } + }, + + onChange(state) { + this.setState(state); + }, + + loadPiece() { + PieceActions.fetchOne(this.props.params.pieceId); + }, + + render() { + if('title' in this.state.piece) { + return ( + +
+

{this.state.piece.title}

+ + +
+
+ }> + + + ); + } else { + return ( +
+ +
+ ); + } + } +}); + + +let CylandPieceDetails = React.createClass({ + propTypes: { + piece: React.PropTypes.object + }, + + render() { + if (Object.keys(this.props.piece.extra_data).length !== 0){ + return ( + +
+ {Object.keys(this.props.piece.extra_data).map((data) => { + let label = data.replace('_', ' '); + return ( + + + ); + } + )} + +
+ +
+ ); + } + return null; + } +}); + +export default CylandPieceContainer; diff --git a/js/components/whitelabel/wallet/components/ascribe_forms/cyland_additional_data_form.js b/js/components/whitelabel/wallet/components/cyland/ascribe_forms/cyland_additional_data_form.js similarity index 85% rename from js/components/whitelabel/wallet/components/ascribe_forms/cyland_additional_data_form.js rename to js/components/whitelabel/wallet/components/cyland/ascribe_forms/cyland_additional_data_form.js index 0ae5e22a..364360c8 100644 --- a/js/components/whitelabel/wallet/components/ascribe_forms/cyland_additional_data_form.js +++ b/js/components/whitelabel/wallet/components/cyland/ascribe_forms/cyland_additional_data_form.js @@ -2,19 +2,19 @@ import React from 'react'; -import Form from '../../../../ascribe_forms/form'; -import Property from '../../../../ascribe_forms/property'; +import Form from '../../../../../ascribe_forms/form'; +import Property from '../../../../../ascribe_forms/property'; -import InputTextAreaToggable from '../../../../ascribe_forms/input_textarea_toggable'; +import InputTextAreaToggable from '../../../../../ascribe_forms/input_textarea_toggable'; -import FurtherDetailsFileuploader from '../../../../ascribe_detail/further_details_fileuploader'; +import FurtherDetailsFileuploader from '../../../../../ascribe_detail/further_details_fileuploader'; -import ApiUrls from '../../../../../constants/api_urls'; -import AppConstants from '../../../../../constants/application_constants'; +import ApiUrls from '../../../../../../constants/api_urls'; +import AppConstants from '../../../../../../constants/application_constants'; -import requests from '../../../../../utils/requests'; +import requests from '../../../../../../utils/requests'; -import { getLangText } from '../../../../../utils/lang_utils'; +import { getLangText } from '../../../../../../utils/lang_utils'; let CylandAdditionalDataForm = React.createClass({ propTypes: { @@ -107,7 +107,7 @@ let CylandAdditionalDataForm = React.createClass({ editable={true} pieceId={this.props.piece.id} otherData={this.props.piece.other_data} - multiple={false}/> + multiple={true}/> ); } else { diff --git a/js/components/whitelabel/wallet/components/cyland/cyland_piece_list.js b/js/components/whitelabel/wallet/components/cyland/cyland_piece_list.js new file mode 100644 index 00000000..018a3e55 --- /dev/null +++ b/js/components/whitelabel/wallet/components/cyland/cyland_piece_list.js @@ -0,0 +1,42 @@ +'use strict'; + +import React from 'react'; +import PieceList from '../../../../piece_list'; + +import UserActions from '../../../../../actions/user_actions'; +import UserStore from '../../../../../stores/user_store'; + +import CylandAccordionListItem from './ascribe_accordion_list/cyland_accordion_list_item'; + + +let CylandPieceList = React.createClass({ + getInitialState() { + return UserStore.getState(); + }, + + componentDidMount() { + UserStore.listen(this.onChange); + UserActions.fetchCurrentUser(); + }, + + componentWillUnmount() { + UserStore.unlisten(this.onChange); + }, + + onChange(state) { + this.setState(state); + }, + + render() { + return ( +
+ +
+ ); + } +}); + +export default CylandPieceList; diff --git a/js/components/whitelabel/wallet/components/cyland/cyland_register_piece.js b/js/components/whitelabel/wallet/components/cyland/cyland_register_piece.js index 3026fc6f..b01d648d 100644 --- a/js/components/whitelabel/wallet/components/cyland/cyland_register_piece.js +++ b/js/components/whitelabel/wallet/components/cyland/cyland_register_piece.js @@ -13,6 +13,9 @@ import RegisterPieceForm from '../../../../ascribe_forms/form_register_piece'; import Property from '../../../../ascribe_forms/property'; import InputCheckbox from '../../../../ascribe_forms/input_checkbox'; +import WhitelabelActions from '../../../../../actions/whitelabel_actions'; +import WhitelabelStore from '../../../../../stores/whitelabel_store'; + import PieceListStore from '../../../../../stores/piece_list_store'; import PieceListActions from '../../../../../actions/piece_list_actions'; @@ -25,7 +28,7 @@ import PieceActions from '../../../../../actions/piece_actions'; import GlobalNotificationModel from '../../../../../models/global_notification_model'; import GlobalNotificationActions from '../../../../../actions/global_notification_actions'; -import CylandAdditionalDataForm from '../ascribe_forms/cyland_additional_data_form'; +import CylandAdditionalDataForm from './ascribe_forms/cyland_additional_data_form'; import LoanForm from '../../../../ascribe_forms/form_loan'; @@ -46,6 +49,7 @@ let CylandRegisterPiece = React.createClass({ UserStore.getState(), PieceListStore.getState(), PieceStore.getState(), + WhitelabelStore.getState(), { selectedLicense: 0, isFineUploaderActive: false @@ -56,14 +60,16 @@ let CylandRegisterPiece = React.createClass({ PieceListStore.listen(this.onChange); UserStore.listen(this.onChange); PieceStore.listen(this.onChange); - + WhitelabelStore.listen(this.onChange); UserActions.fetchCurrentUser(); + WhitelabelActions.fetchWhitelabel(); }, componentWillUnmount() { PieceListStore.unlisten(this.onChange); UserStore.unlisten(this.onChange); PieceStore.unlisten(this.onChange); + WhitelabelStore.unlisten(this.onChange); }, onChange(state) { @@ -105,7 +111,7 @@ let CylandRegisterPiece = React.createClass({ handleLoanSuccess(response) { let notification = new GlobalNotificationModel(response.notification, 'success', 10000); GlobalNotificationActions.appendGlobalNotification(notification); - + PieceActions.fetchOne(this.state.piece.id); this.transitionTo('piece', {pieceId: this.state.piece.id}); }, @@ -177,7 +183,7 @@ let CylandRegisterPiece = React.createClass({ message={getAclFormMessage('acl_loan', '\"' + this.state.piece.title + '\"', this.state.currentUser.username)} id={{piece_id: this.state.piece.id}} url={ApiUrls.ownership_loans_pieces} - email="videoarchive@mailinator.com" + email={this.state.whitelabel.user} gallery="Cyland Archive" startdate={today} enddate={datetimeWhenWeAllWillBeFlyingCoolHoverboardsAndDinosaursWillLiveAgain} diff --git a/js/components/whitelabel/wallet/constants/wallet_api_urls.js b/js/components/whitelabel/wallet/constants/wallet_api_urls.js index 47c05c0a..cd3e4fdb 100644 --- a/js/components/whitelabel/wallet/constants/wallet_api_urls.js +++ b/js/components/whitelabel/wallet/constants/wallet_api_urls.js @@ -1,8 +1,16 @@ 'use strict'; +import walletConstants from './wallet_application_constants'; + // gets subdomain as a parameter -function getPrizeApiUrls() { +function getWalletApiUrls(subdomain) { + if (subdomain === 'cyland'){ + return { + 'pieces_list': walletConstants.walletApiEndpoint + subdomain + '/pieces/', + 'piece': walletConstants.walletApiEndpoint + subdomain + '/pieces/${piece_id}/' + }; + } return {}; } -export default getPrizeApiUrls; \ No newline at end of file +export default getWalletApiUrls; \ No newline at end of file diff --git a/js/components/whitelabel/wallet/constants/wallet_application_constants.js b/js/components/whitelabel/wallet/constants/wallet_application_constants.js index bc0d73fd..cec456d9 100644 --- a/js/components/whitelabel/wallet/constants/wallet_application_constants.js +++ b/js/components/whitelabel/wallet/constants/wallet_application_constants.js @@ -3,7 +3,7 @@ import AppConstants from '../../../../constants/application_constants'; let walletConstants = { - walletApiEndpoint: AppConstants.apiEndpoint + 'wallets/' + walletApiEndpoint: AppConstants.apiEndpoint + 'whitelabel/' }; export default walletConstants; \ No newline at end of file diff --git a/js/components/whitelabel/wallet/wallet_app.js b/js/components/whitelabel/wallet/wallet_app.js index 15b115d6..27657ff7 100644 --- a/js/components/whitelabel/wallet/wallet_app.js +++ b/js/components/whitelabel/wallet/wallet_app.js @@ -10,7 +10,7 @@ let RouteHandler = Router.RouteHandler; let WalletApp = React.createClass({ render() { return ( -
+
diff --git a/js/components/whitelabel/wallet/wallet_routes.js b/js/components/whitelabel/wallet/wallet_routes.js index a0c80c17..b5821670 100644 --- a/js/components/whitelabel/wallet/wallet_routes.js +++ b/js/components/whitelabel/wallet/wallet_routes.js @@ -14,7 +14,10 @@ import EditionContainer from '../../../components/ascribe_detail/edition_contain import SettingsContainer from '../../../components/settings_container'; // specific components +import CylandPieceContainer from './components/cyland/ascribe_detail/cyland_piece_container'; import CylandRegisterPiece from './components/cyland/cyland_register_piece'; +import CylandPieceList from './components/cyland/cyland_piece_list'; + import CCRegisterPiece from './components/cc/cc_register_piece'; import WalletApp from './wallet_app'; @@ -34,8 +37,8 @@ let ROUTES = { - - + + diff --git a/js/constants/application_constants.js b/js/constants/application_constants.js index acd2561a..530aaece 100644 --- a/js/constants/application_constants.js +++ b/js/constants/application_constants.js @@ -12,7 +12,7 @@ let constants = { 'baseUrl': window.BASE_URL, 'aclList': ['acl_coa', 'acl_consign', 'acl_delete', 'acl_download', 'acl_edit', 'acl_create_editions', 'acl_view_editions', 'acl_loan', 'acl_share', 'acl_transfer', 'acl_unconsign', 'acl_unshare', 'acl_view', - 'acl_withdraw_transfer', 'acl_submit_to_prize'], + 'acl_withdraw_transfer', 'acl_submit'], 'version': 0.1, 'csrftoken': 'csrftoken2', @@ -25,13 +25,6 @@ let constants = { 'type': 'wallet', 'ga': 'UA-60614729-4' }, - { - 'subdomain': 'cc-staging', - 'name': 'Creative Commons France', - 'logo': 'https://s3-us-west-2.amazonaws.com/ascribe0/public/creativecommons/cc.logo.sm.png', - 'permissions': ['register', 'edit', 'share', 'del_from_collection'], - 'type': 'wallet' - }, { 'subdomain': 'sluice', 'name': 'Sluice Art Fair', @@ -40,13 +33,6 @@ let constants = { 'type': 'prize', 'ga': 'UA-60614729-5' }, - { - 'subdomain': 'sluice-staging', - 'name': 'Sluice Art Fair', - 'logo': 'https://s3-us-west-2.amazonaws.com/ascribe0/whitelabel/sluice/logo.jpeg', - 'permissions': ['register', 'edit', 'share', 'del_from_collection'], - 'type': 'prize' - }, { 'subdomain': 'cyland', 'name': 'Cyland media art lab',