From d1d2aa5601639b8fe4b4fed7511451378dca01e4 Mon Sep 17 00:00:00 2001 From: Matt Zikherman Date: Mon, 11 Dec 2017 16:39:33 -0500 Subject: [PATCH 01/12] [Gene] Seperate artists and artworks. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Eloy Durán --- package.json | 6 +- src/Components/ArtworkFilter/Dropdown.tsx | 12 +- src/Components/Gene/Artists.tsx | 80 +++++++- src/Components/Gene/Artworks.tsx | 236 ++++++++++++++++++++++ src/Components/Gene/Contents.tsx | 8 +- src/Components/Gene/NewContents.tsx | 104 ++++++++++ src/Components/__stories__/Gene.story.tsx | 16 +- 7 files changed, 445 insertions(+), 17 deletions(-) create mode 100644 src/Components/Gene/Artworks.tsx create mode 100644 src/Components/Gene/NewContents.tsx diff --git a/package.json b/package.json index 25b577d4d1..50e7ff4584 100644 --- a/package.json +++ b/package.json @@ -32,10 +32,10 @@ "compile": "env GRAPHQL_NO_NAME_WARNING=true gulp compile", "prepublishOnly": "rm -rf dist && npm run compile", "precommit": "lint-staged", - "prepush": "npm run type-check", + "prepush": "yarn run type-check", "prettier": "prettier", - "prettier-write": "npm run prettier --write", - "prettier-project": "npm run prettier-write -- 'src/**/*.{ts,tsx}'" + "prettier-write": "yarn run prettier --write", + "prettier-project": "yarn run prettier-write 'src/**/*.{ts,tsx}'" }, "prettier": { "printWidth": 120, diff --git a/src/Components/ArtworkFilter/Dropdown.tsx b/src/Components/ArtworkFilter/Dropdown.tsx index 3d75e76972..fb69dd5945 100644 --- a/src/Components/ArtworkFilter/Dropdown.tsx +++ b/src/Components/ArtworkFilter/Dropdown.tsx @@ -13,7 +13,7 @@ import { find } from "lodash" interface DropdownProps extends RelayProps, React.HTMLProps { aggregation: any - onSelect?: any + onSelected?: (slice: string, value: string) => void selected?: any } @@ -41,12 +41,12 @@ export class Dropdown extends React.Component { }) } - onSelect(count, slice) { + onSelect(slice: string, value: string) { this.setState({ - selected: count.id, + selected: value, isHovered: false, }) - this.props.onSelect(count, slice) + this.props.onSelected(slice, value) } getSelectedName(id) { @@ -61,7 +61,7 @@ export class Dropdown extends React.Component { let navItems = this.props.aggregation.counts.map(count => { return ( - this.onSelect(count, slice)}> + this.onSelect(slice, count.id)}> {count.name}  ({numeral(count.count).format("0,0")}) @@ -69,7 +69,7 @@ export class Dropdown extends React.Component { }) navItems.unshift( - this.onSelect({ value: "*" }, slice)}> + this.onSelect(slice, "*")}> All {labels.plural} ) diff --git a/src/Components/Gene/Artists.tsx b/src/Components/Gene/Artists.tsx index df5dd2dfe5..b7bfa51826 100644 --- a/src/Components/Gene/Artists.tsx +++ b/src/Components/Gene/Artists.tsx @@ -7,10 +7,16 @@ import * as fonts from "../../Assets/Fonts" import Spinner from "../Spinner" import ArtistRow from "./ArtistRow" +import Dropdown from "../ArtworkFilter/Dropdown" + +import { ButtonState } from "../Buttons/Default" +import Button from "../Buttons/Ghost" + const PageSize = 10 interface Props extends RelayProps { relay?: RelayPaginationProp + onDropdownSelected: (slice: string, value: string) => void } interface State { @@ -44,6 +50,23 @@ const SpinnerContainer = styled.div` position: relative; ` +const ArtistFilterButtons = styled.div` +margin-right: 10px; +button { + height: 52px; + padding: 16px; +} +` + +const FilterBar = styled.div` +vertical-align: middle; +text-align: center; + +> div { + display: inline-block; +} +` + export class Artists extends React.Component { state = { loading: false, @@ -60,6 +83,37 @@ export class Artists extends React.Component { } } + renderArtistFilter() { + return ( + + By Artists: + + By Work: + + ) + } + + renderArtistDropdown() { + return this.props.gene.filter_aggregations.aggregations.map(aggregation => { + return ( + + ) + }) + } + + render() { const artists = this.props.gene.artists @@ -74,11 +128,16 @@ export class Artists extends React.Component { ) return ( +
+ + {this.renderArtistFilter()} + {this.renderArtistDropdown()} + {artistRows} {this.state.loading ? : ""} {artists && artists.pageInfo.hasNextPage && !this.state.loading && loadMoreButton} - +
) } } @@ -88,7 +147,7 @@ export default createPaginationContainer( { gene: graphql.experimental` fragment Artists_gene on Gene - @argumentDefinitions(count: { type: "Int", defaultValue: 10 }, cursor: { type: "String", defaultValue: "" }) { + @argumentDefinitions(aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] }, count: { type: "Int", defaultValue: 10 }, cursor: { type: "String", defaultValue: "" }) { __id artists: artists_connection(first: $count, after: $cursor) @connection(key: "Artists_artists") { pageInfo { @@ -101,6 +160,13 @@ export default createPaginationContainer( } } } + filter_aggregations: filtered_artworks(aggregations: $aggregations, size: 0) { + ...TotalCount_filter_artworks + aggregations { + slice + ...Dropdown_aggregation + } + } } `, }, @@ -122,12 +188,13 @@ export default createPaginationContainer( ...fragmentVariables, count, cursor, + geneNodeID: props.gene.__id, } }, query: graphql.experimental` - query ArtistsQuery($geneNodeID: ID!, $count: Int!, $cursor: String) { + query ArtistsQuery($geneNodeID: ID!, $count: Int!, $cursor: String, $aggregations: [ArtworkAggregation]) { node(__id: $geneNodeID) { - ...Artists_gene @arguments(count: $count, cursor: $cursor) + ...Artists_gene @arguments(count: $count, cursor: $cursor, aggregations: $aggregations) } } `, @@ -147,5 +214,10 @@ interface RelayProps { } }> } + filter_aggregations: { + aggregations: Array<{ + slice: string + }> + } } } diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/Artworks.tsx new file mode 100644 index 0000000000..90dac6f4c2 --- /dev/null +++ b/src/Components/Gene/Artworks.tsx @@ -0,0 +1,236 @@ +import * as React from "react" +import { ConnectionData } from "react-relay" +import { createPaginationContainer, graphql, RelayPaginationProp } from "react-relay" +import styled from "styled-components" + +import Spinner from "../Spinner" + +import Dropdown from "../ArtworkFilter/Dropdown" +import ForSaleCheckbox from "../ArtworkFilter/ForSaleCheckbox" + +import Headline from "../ArtworkFilter/Headline" +import TotalCount from "../ArtworkFilter/TotalCount" + +import BorderedPulldown from "../BorderedPulldown" + +import ArtworkGrid from "../ArtworkGrid" + +const PageSize = 10 + +interface Filters { + for_sale?: boolean + dimension_range?: string + price_range?: string + medium?: string +} + +interface Props extends RelayProps, Filters { + relay?: RelayPaginationProp + onDropdownSelected: (slice: string, value: string) => void +} + +interface State { + loading: boolean +} + +const FilterBar = styled.div` + vertical-align: middle; + text-align: center; + + > div { + display: inline-block; + } +` + +const SubFilterBar = styled.div` + display: flex; + justify-content: space-between; + padding: 40px 0 20px; + align-items: center; +` + +const SpinnerContainer = styled.div` + width: 100%; + height: 100px; + position: relative; +` + +export class Artworks extends React.Component { + state = { + loading: false, + } + + renderDropdown() { + return this.props.gene.filtered_artworks.aggregations.map(aggregation => { + return ( + + ) + }) + } + + renderForSaleToggle() { + return null} /> + } + + renderArtworks() { + const pulldownOptions = [ + { val: "-partner_updated_at", name: "Recently Updated" }, + { val: "-year", name: "Artwork Year (desc.)" }, + { val: "year", name: "Artwork Year (asc.)" }, + ] + return ( +
+ +
+ + +
+ null} /> +
+ null} + /> + {this.state.loading ? : ""} +
+ ) + } + + render() { + return ( +
+ + {this.renderForSaleToggle()} + {this.renderDropdown()} + + {this.renderArtworks()} +
+ ) + } +} + +export default createPaginationContainer( + Artworks, + { + gene: graphql.experimental` + fragment Artworks_gene on Gene + @argumentDefinitions( + count: { type: "Int", defaultValue: 10 } + cursor: { type: "String", defaultValue: "" } + sort: { type: "String", defaultValue: "-partner_updated_at" } + for_sale: { type: "Boolean" } + medium: { type: "String", defaultValue: "*" } + aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] } + price_range: { type: "String", defaultValue: "*" } + dimension_range: { type: "String", defaultValue: "*" } + ) { + filtered_artworks( + aggregations: $aggregations + size: $count + for_sale: $for_sale + medium: $medium + price_range: $price_range + dimension_range: $dimension_range + sort: $sort + ) { + ...TotalCount_filter_artworks + aggregations { + slice + ...Dropdown_aggregation + } + artworks: artworks_connection(first: $count, after: $cursor) @connection(key: "Artworks_artworks") { + pageInfo { + hasNextPage + endCursor + } + edges { + node { + __id + } + } + ...ArtworkGrid_artworks + } + } + } + `, + }, + { + direction: "forward", + getConnectionFromProps(props) { + return props.gene.filtered_artworks.artworks as ConnectionData + }, + getFragmentVariables(prevVars, totalCount) { + return { + ...prevVars, + count: totalCount, + } + }, + getVariables(props, { count, cursor }, fragmentVariables) { + return { + // in most cases, for variables other than connection filters like + // `first`, `after`, etc. you may want to use the previous values. + ...fragmentVariables, + count, + cursor, + geneNodeID: props.gene.__id, + } + }, + query: graphql.experimental` + query ArtworksQuery( + $geneNodeID: ID! + $count: Int! + $cursor: String + $showArtists: Boolean + $sort: String + $for_sale: Boolean + $medium: String + $aggregations: [ArtworkAggregation] + $price_range: String + $dimension_range: String + ) { + node(__id: $geneNodeID) { + ...Artworks_gene + @arguments( + count: $count + cursor: $cursor + showArtists: $showArtists + sort: $sort + for_sale: $for_sale + medium: $medium + aggregations: $aggregations + price_range: $price_range + dimension_range: $dimension_range + ) + } + } + `, + } +) + +interface RelayProps { + gene: { + __id: string + filtered_artworks: { + aggregations: Array<{ + slice: string + }> + artworks: { + edges: Array<{}> + } + } + } +} diff --git a/src/Components/Gene/Contents.tsx b/src/Components/Gene/Contents.tsx index 92370ddb91..97b222d13f 100644 --- a/src/Components/Gene/Contents.tsx +++ b/src/Components/Gene/Contents.tsx @@ -35,6 +35,7 @@ interface State { price_range: string medium: string loading: boolean + showArtists: boolean } const urlPropsQueryConfig = { @@ -53,6 +54,7 @@ export class GeneContents extends React.Component { price_range: props.price_range || "*", medium: props.medium || "*", loading: false, + showArtists: true, } } @@ -166,7 +168,7 @@ export class GeneContents extends React.Component { render() { const { filtered_artworks, mode } = this.props.gene - const { showArtists } = this.context.relay.variables + const { showArtists } = this.state const shouldShowArtists = showArtists && !this.anyArtworkFilters() const dropdowns = filtered_artworks.aggregations.map(aggregation => { @@ -175,7 +177,7 @@ export class GeneContents extends React.Component { aggregation={aggregation} key={aggregation.slice} selected={aggregation.slice && this.state[aggregation.slice.toLowerCase()]} - onSelect={(count, slice) => this.onSelect(count, slice)} + onSelected={(count, slice) => this.onSelect(count, slice)} /> ) }) @@ -316,7 +318,7 @@ export default createPaginationContainer( ... on Gene @include(if: $showArtists) { ...Artists_gene } - filtered_artworks( + old_filtered_artworks: filtered_artworks( aggregations: $aggregations size: $count for_sale: $for_sale diff --git a/src/Components/Gene/NewContents.tsx b/src/Components/Gene/NewContents.tsx new file mode 100644 index 0000000000..527f210d43 --- /dev/null +++ b/src/Components/Gene/NewContents.tsx @@ -0,0 +1,104 @@ +import React from "react" +import { graphql, QueryRenderer } from "react-relay" + +import { ContextConsumer, ContextProps } from "../Artsy" +import Artists from "./Artists" +import Artworks from "./Artworks" + +interface Filters { + for_sale: boolean + dimension_range: string + price_range: string + medium: string +} + +interface Props extends ContextProps { + mode: "artists" | "artworks" + filters?: Filters + geneID: string +} + +interface State extends Filters { + mode: "artists" | "artworks" +} + +class GeneNewContents extends React.Component { + constructor(props: Props) { + super(props) + this.state = { + for_sale: null, + medium: "*", + price_range: "*", + dimension_range: "*", + mode: props.mode, + } + } + + onDropdownSelect(slice: string, value: string) { + this.setState({ + [slice.toLowerCase()]: value, + mode: "artworks", + }) + } + + renderArtists() { + const { geneID, relayEnvironment } = this.props + return ( + { + if (props) { + return + } else { + return null + } + }} + /> + ) + } + + renderArtworks() { + const { geneID, relayEnvironment } = this.props + return ( + { + if (props) { + return + } else { + return null + } + }} + /> + ) + } + + render() { + const { filters } = this.props + const { mode } = this.state + if (mode === "artists" && !filters) { + return this.renderArtists() + } + return this.renderArtworks() + } +} + +export const NewContents = ContextConsumer(GeneNewContents) diff --git a/src/Components/__stories__/Gene.story.tsx b/src/Components/__stories__/Gene.story.tsx index d531a115aa..f49dcd84be 100644 --- a/src/Components/__stories__/Gene.story.tsx +++ b/src/Components/__stories__/Gene.story.tsx @@ -5,6 +5,9 @@ import { graphql } from "react-relay" import { RootQueryRenderer } from "../../Relay/RootQueryRenderer" import Gene from "../Gene" import ArtistRow from "../Gene/ArtistRow" +import { NewContents } from "../Gene/NewContents" + +import { ContextProvider } from "../Artsy" function GeneExample(props: { geneID: string }) { return ( @@ -16,7 +19,7 @@ function GeneExample(props: { geneID: string }) { } } `} - variables={{ artistID: props.geneID }} + variables={{ geneID: props.geneID }} render={readyState => readyState.props && } /> ) @@ -83,3 +86,14 @@ storiesOf("Components/Pages/Gene", module) ) }) + + storiesOf("Components/Pages/Gene/NewContents", module) + .add("Integration - Minimalism", () => { + return ( +
+ < ContextProvider currentUser={{id: "matt-z", name: "Matt", accessToken: "REPLACE_ME"}}> + + +
+ ) + }) From 77b544de84775c07e527f6bbf62b278f8703ce1c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Eloy=20Dur=C3=A1n?= Date: Mon, 11 Dec 2017 19:57:49 -0500 Subject: [PATCH 02/12] [Gene] Fix type issue with dynamic object key typing. See https://stackoverflow.com/questions/42090191/picks-k-type-with-dynamic-computed-keys/42131589#42131589 --- src/Components/Gene/NewContents.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Components/Gene/NewContents.tsx b/src/Components/Gene/NewContents.tsx index 527f210d43..e9ae0b7dd8 100644 --- a/src/Components/Gene/NewContents.tsx +++ b/src/Components/Gene/NewContents.tsx @@ -36,7 +36,7 @@ class GeneNewContents extends React.Component { onDropdownSelect(slice: string, value: string) { this.setState({ - [slice.toLowerCase()]: value, + [slice.toLowerCase() as any]: value, mode: "artworks", }) } From e28ad169dff9aa56484eae1fa88a46476922835d Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Tue, 12 Dec 2017 13:04:35 -0500 Subject: [PATCH 03/12] wip- artworks filtering and headline --- data/schema.graphql | 228 +- data/schema.json | 2458 ++++++++++++++++++--- externals/metaphysics | 2 +- src/Components/ArtworkFilter/Headline.tsx | 4 +- src/Components/Gene/Artworks.tsx | 26 +- src/Components/Gene/NewContents.tsx | 3 +- src/Components/__stories__/Gene.story.tsx | 2 +- 7 files changed, 2430 insertions(+), 293 deletions(-) diff --git a/data/schema.graphql b/data/schema.graphql index 92028e5043..45f5f154d8 100644 --- a/data/schema.graphql +++ b/data/schema.graphql @@ -92,6 +92,7 @@ type Artist implements Node { exclude: [String] ): [Artwork] artworks_connection(sort: ArtworkSorts, filter: [ArtistArtworksFilters], published: Boolean = true, after: String, first: Int, before: String, last: Int): ArtworkConnection + auctionResults(sort: AuctionResultSorts, after: String, first: Int, before: String, last: Int): AuctionResultConnection bio: String # The Artist biography article written by Artsy @@ -104,6 +105,7 @@ type Artist implements Node { birthday: String blurb(format: Format): String carousel: ArtistCarousel + collections: [String] contemporary( # The number of Artists to return size: Int @@ -142,6 +144,7 @@ type Artist implements Node { meta: ArtistMeta nationality: String name: String + partners(represented_by: Boolean, partner_category: [String], after: String, first: Int, before: String, last: Int): PartnerArtistConnection partner_artists( # The number of PartnerArtists to return size: Int @@ -259,7 +262,7 @@ type ArtistEdge { } type ArtistHighlights { - partner_artists(represented_by: Boolean, partner_category: [String]): [PartnerArtist] + partners(represented_by: Boolean, partner_category: [String], after: String, first: Int, before: String, last: Int): PartnerArtistConnection } type ArtistItem implements Node { @@ -289,6 +292,7 @@ type ArtistItem implements Node { exclude: [String] ): [Artwork] artworks_connection(sort: ArtworkSorts, filter: [ArtistArtworksFilters], published: Boolean = true, after: String, first: Int, before: String, last: Int): ArtworkConnection + auctionResults(sort: AuctionResultSorts, after: String, first: Int, before: String, last: Int): AuctionResultConnection bio: String # The Artist biography article written by Artsy @@ -301,6 +305,7 @@ type ArtistItem implements Node { birthday: String blurb(format: Format): String carousel: ArtistCarousel + collections: [String] contemporary( # The number of Artists to return size: Int @@ -339,6 +344,7 @@ type ArtistItem implements Node { meta: ArtistMeta nationality: String name: String + partners(represented_by: Boolean, partner_category: [String], after: String, first: Int, before: String, last: Int): PartnerArtistConnection partner_artists( # The number of PartnerArtists to return size: Int @@ -419,6 +425,7 @@ type ArtistSearchEntity implements Node { exclude: [String] ): [Artwork] artworks_connection(sort: ArtworkSorts, filter: [ArtistArtworksFilters], published: Boolean = true, after: String, first: Int, before: String, last: Int): ArtworkConnection + auctionResults(sort: AuctionResultSorts, after: String, first: Int, before: String, last: Int): AuctionResultConnection bio: String # The Artist biography article written by Artsy @@ -431,6 +438,7 @@ type ArtistSearchEntity implements Node { birthday: String blurb(format: Format): String carousel: ArtistCarousel + collections: [String] contemporary( # The number of Artists to return size: Int @@ -469,6 +477,7 @@ type ArtistSearchEntity implements Node { meta: ArtistMeta nationality: String name: String + partners(represented_by: Boolean, partner_category: [String], after: String, first: Int, before: String, last: Int): PartnerArtistConnection partner_artists( # The number of PartnerArtists to return size: Int @@ -746,6 +755,9 @@ type ArtworkContextAuction implements Node { # Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header timezone: String ): String + + # Returns a live auctions url if the sale is open and start time is after now + live_url_if_open: String profile: Profile registration_ends_at( convert_to_utc: Boolean @@ -978,6 +990,9 @@ type ArtworkContextSale implements Node { # Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header timezone: String ): String + + # Returns a live auctions url if the sale is open and start time is after now + live_url_if_open: String profile: Profile registration_ends_at( convert_to_utc: Boolean @@ -1011,7 +1026,24 @@ type ArtworkEdge { cursor: String! } -union ArtworkFilterFacet = ArtworkFilterTag +union ArtworkFilterFacet = ArtworkFilterTag | ArtworkFilterGene + +type ArtworkFilterGene { + # A globally unique ID. + __id: ID! + + # A type-specific ID. + id: String! + + # A type-specific Gravity Mongo Document ID. + _id: String! + cached: Int + description: String + name: String + href: String + image: Image + count: Int +} type ArtworkFilterTag { # A globally unique ID. @@ -1363,6 +1395,109 @@ type Attachment { download_url: String! } +# In centimeters. +type AuctionLotDimensions { + width: Float + height: Float + depth: Float +} + +type AuctionLotImages { + larger: Image + thumbnail: Image +} + +type AuctionResult implements Node { + # A globally unique ID. + __id: ID! + + # A type-specific ID. + id: String! + title: String + artist_id: String! + date( + convert_to_utc: Boolean + format: String + + # Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header + timezone: String + ): String + date_text: String + medium_text: String + category_text: String + dimension_text: String + dimensions: AuctionLotDimensions + organization: String + sale_date( + convert_to_utc: Boolean + format: String + + # Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header + timezone: String + ): String + sale_date_text: String + sale_title: String + currency: String + description: String + external_url: String + images: AuctionLotImages + + # A formatted price with various currency formatting options. + low_estimate( + decimal: String = "." + + # Allows control of symbol position (%v = value, %s = symbol) + format: String = "%s%v" + precision: Int = 0 + symbol: String + thousand: String = "," + ): String + + # A formatted price with various currency formatting options. + high_estimate( + decimal: String = "." + + # Allows control of symbol position (%v = value, %s = symbol) + format: String = "%s%v" + precision: Int = 0 + symbol: String + thousand: String = "," + ): String + + # A formatted price with various currency formatting options. + price_realized( + decimal: String = "." + + # Allows control of symbol position (%v = value, %s = symbol) + format: String = "%s%v" + precision: Int = 0 + symbol: String + thousand: String = "," + ): String +} + +# A connection to a list of items. +type AuctionResultConnection { + # Information to aid in pagination. + pageInfo: PageInfo! + + # A list of edges. + edges: [AuctionResultEdge] +} + +# An edge in a connection. +type AuctionResultEdge { + # The item at the end of the edge + node: AuctionResult + + # A cursor for use in pagination + cursor: String! +} + +enum AuctionResultSorts { + PRICE_AND_DATE_DESC +} + type Author { # A globally unique ID. __id: ID! @@ -1676,6 +1811,10 @@ type ConsignmentSubmissionEdge { cursor: String! } +type Convection { + geminiTemplateKey: String! +} + # A conversation. type Conversation implements Node { # A globally unique ID. @@ -2214,6 +2353,35 @@ type FollowArtists { counts: FollowArtistCounts } +type FollowedArtistsArtworksGroup implements Node { + # A globally unique ID. + __id: ID! + + # List of artworks in this group. + artworks: [Artwork] + artists: String + summary: String + image: Image +} + +# A connection to a list of items. +type FollowedArtistsArtworksGroupConnection { + # Information to aid in pagination. + pageInfo: PageInfo! + + # A list of edges. + edges: [FollowedArtistsArtworksGroupEdge] +} + +# An edge in a connection. +type FollowedArtistsArtworksGroupEdge { + # The item at the end of the edge + node: FollowedArtistsArtworksGroup + + # A cursor for use in pagination + cursor: String! +} + type FollowGene { gene: Gene @@ -2252,6 +2420,11 @@ type FollowGenePayload { clientMutationId: String } +type FollowsAndSaves { + # A list of published artworks by followed artists (grouped by date and artists). + bundledArtworksByArtist(sort: ArtworkSorts, after: String, first: Int, before: String, last: Int): FollowedArtistsArtworksGroupConnection +} + enum Format { HTML PLAIN @@ -3010,6 +3183,9 @@ type HomePageModuleContextSale implements Node { # Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header timezone: String ): String + + # Returns a live auctions url if the sale is open and start time is after now + live_url_if_open: String profile: Profile registration_ends_at( convert_to_utc: Boolean @@ -3239,6 +3415,7 @@ type Me implements Node { # A list of the current user’s inquiry requests followed_genes(after: String, first: Int, before: String, last: Int): FollowGeneConnection + followsAndSaves: FollowsAndSaves # An invoice invoice( @@ -3270,7 +3447,7 @@ type Me implements Node { initials(length: Int = 3): String # A list of feed items, indicating published artworks (grouped by date and artists). - notifications_connection(after: String, first: Int, before: String, last: Int): NotificationsFeedItemConnection + notifications_connection(after: String, first: Int, before: String, last: Int): NotificationsFeedItemConnection @deprecated(reason: "Prefer to use followed_artists_artwork_groups.") paddle_number: String sale_registrations( # Limit by auction. @@ -3536,6 +3713,15 @@ type PartnerArtist { sortable_id: String } +# A connection to a list of items. +type PartnerArtistConnection { + # Information to aid in pagination. + pageInfo: PageInfo! + + # A list of edges. + edges: [PartnerArtistEdge] +} + type PartnerArtistCounts { artworks( # Returns a `String` when format is specified. e.g.`'0,0.0000''` @@ -3549,6 +3735,29 @@ type PartnerArtistCounts { ): FormattedNumber } +# An edge in a connection. +type PartnerArtistEdge { + # The item at the end of the edge + node: Partner + + # A cursor for use in pagination + cursor: String! + + # A globally unique ID. + __id: ID! + + # A type-specific ID. + id: String! + artist: Artist + biography: String + counts: PartnerArtistCounts + is_display_on_partner_profile: Boolean + is_represented_by: Boolean + is_use_default_biography: Boolean + partner: Partner + sortable_id: String +} + type PartnerCategory { # A globally unique ID. __id: ID! @@ -4257,6 +4466,9 @@ type Query { term: String! ): Search + # The schema for difference microservice settings + services: Services + # A Show show( # The slug or ID of the Show @@ -4441,6 +4653,9 @@ type Sale implements Node { # Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header timezone: String ): String + + # Returns a live auctions url if the sale is open and start time is after now + live_url_if_open: String profile: Profile registration_ends_at( convert_to_utc: Boolean @@ -4786,6 +5001,10 @@ type SendConversationMessageMutationPayload { clientMutationId: String } +type Services { + convection: Convection! +} + type Show implements Node { # A globally unique ID. __id: ID! @@ -5493,6 +5712,9 @@ type Viewer { term: String! ): Search + # The schema for difference microservice settings + services: Services + # A Show show( # The slug or ID of the Show diff --git a/data/schema.json b/data/schema.json index b1258ddbf9..dbf7d220c7 100644 --- a/data/schema.json +++ b/data/schema.json @@ -2141,6 +2141,18 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "services", + "description": "The schema for difference microservice settings", + "args": [], + "type": { + "kind": "OBJECT", + "name": "Services", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "show", "description": "A Show", @@ -2637,6 +2649,11 @@ "name": "Artist", "ofType": null }, + { + "kind": "OBJECT", + "name": "AuctionResult", + "ofType": null + }, { "kind": "OBJECT", "name": "Show", @@ -2737,6 +2754,11 @@ "name": "Invoice", "ofType": null }, + { + "kind": "OBJECT", + "name": "FollowedArtistsArtworksGroup", + "ofType": null + }, { "kind": "OBJECT", "name": "NotificationsFeedItem", @@ -5181,6 +5203,69 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "auctionResults", + "description": null, + "args": [ + { + "name": "sort", + "description": null, + "type": { + "kind": "ENUM", + "name": "AuctionResultSorts", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "AuctionResultConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "bio", "description": null, @@ -5285,6 +5370,22 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "collections", + "description": null, + "args": [], + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "contemporary", "description": null, @@ -5612,6 +5713,83 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "partners", + "description": null, + "args": [ + { + "name": "represented_by", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "partner_category", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "PartnerArtistConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "partner_artists", "description": null, @@ -6322,67 +6500,53 @@ "possibleTypes": null }, { - "kind": "OBJECT", - "name": "ArtistBlurb", + "kind": "ENUM", + "name": "AuctionResultSorts", "description": null, - "fields": [ - { - "name": "credit", - "description": null, - "args": [], - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "isDeprecated": false, - "deprecationReason": null - }, + "fields": null, + "inputFields": null, + "interfaces": null, + "enumValues": [ { - "name": "text", + "name": "PRICE_AND_DATE_DESC", "description": null, - "args": [], - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "isDeprecated": false, - "deprecationReason": null - }, - { - "name": "partner_id", - "description": "The partner id of the partner who submitted the featured bio.", - "args": [], - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, "isDeprecated": false, "deprecationReason": null } ], - "inputFields": null, - "interfaces": [], - "enumValues": null, "possibleTypes": null }, { "kind": "OBJECT", - "name": "ArtistCarousel", - "description": null, + "name": "AuctionResultConnection", + "description": "A connection to a list of items.", "fields": [ { - "name": "images", - "description": null, + "name": "pageInfo", + "description": "Information to aid in pagination.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "PageInfo", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "edges", + "description": "A list of edges.", "args": [], "type": { "kind": "LIST", "name": null, "ofType": { "kind": "OBJECT", - "name": "Image", + "name": "AuctionResultEdge", "ofType": null } }, @@ -6397,203 +6561,33 @@ }, { "kind": "OBJECT", - "name": "ArtistCounts", - "description": null, + "name": "AuctionResultEdge", + "description": "An edge in a connection.", "fields": [ { - "name": "artworks", - "description": null, - "args": [ - { - "name": "format", - "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - }, - { - "name": "label", - "description": null, - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - } - ], - "type": { - "kind": "SCALAR", - "name": "FormattedNumber", - "ofType": null - }, - "isDeprecated": false, - "deprecationReason": null - }, - { - "name": "follows", - "description": null, - "args": [ - { - "name": "format", - "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - }, - { - "name": "label", - "description": null, - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - } - ], - "type": { - "kind": "SCALAR", - "name": "FormattedNumber", - "ofType": null - }, - "isDeprecated": false, - "deprecationReason": null - }, - { - "name": "for_sale_artworks", - "description": null, - "args": [ - { - "name": "format", - "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - }, - { - "name": "label", - "description": null, - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - } - ], - "type": { - "kind": "SCALAR", - "name": "FormattedNumber", - "ofType": null - }, - "isDeprecated": false, - "deprecationReason": null - }, - { - "name": "partner_shows", - "description": null, - "args": [ - { - "name": "format", - "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - }, - { - "name": "label", - "description": null, - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - } - ], + "name": "node", + "description": "The item at the end of the edge", + "args": [], "type": { - "kind": "SCALAR", - "name": "FormattedNumber", + "kind": "OBJECT", + "name": "AuctionResult", "ofType": null }, "isDeprecated": false, "deprecationReason": null }, { - "name": "related_artists", - "description": null, - "args": [ - { - "name": "format", - "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - }, - { - "name": "label", - "description": null, - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - } - ], + "name": "cursor", + "description": "A cursor for use in pagination", + "args": [], "type": { - "kind": "SCALAR", - "name": "FormattedNumber", - "ofType": null - }, - "isDeprecated": false, - "deprecationReason": null - }, - { - "name": "articles", - "description": null, - "args": [ - { - "name": "format", - "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null - }, - { - "name": "label", - "description": null, - "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null - }, - "defaultValue": null + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null } - ], - "type": { - "kind": "SCALAR", - "name": "FormattedNumber", - "ofType": null }, "isDeprecated": false, "deprecationReason": null @@ -6604,19 +6598,880 @@ "enumValues": null, "possibleTypes": null }, - { - "kind": "SCALAR", - "name": "FormattedNumber", - "description": "The `FormattedNumber` type represents a number that can optionally be returnedas a formatted String. It does not try to coerce the type.", - "fields": null, - "inputFields": null, - "interfaces": null, - "enumValues": null, - "possibleTypes": null - }, { "kind": "OBJECT", - "name": "Show", + "name": "AuctionResult", + "description": null, + "fields": [ + { + "name": "__id", + "description": "A globally unique ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "id", + "description": "A type-specific ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "title", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "artist_id", + "description": null, + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "date", + "description": null, + "args": [ + { + "name": "convert_to_utc", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "format", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "timezone", + "description": "Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "date_text", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "medium_text", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "category_text", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "dimension_text", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "dimensions", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "AuctionLotDimensions", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "organization", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "sale_date", + "description": null, + "args": [ + { + "name": "convert_to_utc", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "format", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "timezone", + "description": "Specify a tz database time zone, otherwise falls back to `X-TIMEZONE` header", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "sale_date_text", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "sale_title", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "currency", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "description", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "external_url", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "images", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "AuctionLotImages", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "low_estimate", + "description": "A formatted price with various currency formatting options.", + "args": [ + { + "name": "decimal", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\".\"" + }, + { + "name": "format", + "description": "Allows control of symbol position (%v = value, %s = symbol)", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\"%s%v\"" + }, + { + "name": "precision", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": "0" + }, + { + "name": "symbol", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "thousand", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\",\"" + } + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "high_estimate", + "description": "A formatted price with various currency formatting options.", + "args": [ + { + "name": "decimal", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\".\"" + }, + { + "name": "format", + "description": "Allows control of symbol position (%v = value, %s = symbol)", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\"%s%v\"" + }, + { + "name": "precision", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": "0" + }, + { + "name": "symbol", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "thousand", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\",\"" + } + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "price_realized", + "description": "A formatted price with various currency formatting options.", + "args": [ + { + "name": "decimal", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\".\"" + }, + { + "name": "format", + "description": "Allows control of symbol position (%v = value, %s = symbol)", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\"%s%v\"" + }, + { + "name": "precision", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": "0" + }, + { + "name": "symbol", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "thousand", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": "\",\"" + } + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [ + { + "kind": "INTERFACE", + "name": "Node", + "ofType": null + } + ], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "AuctionLotDimensions", + "description": "In centimeters.", + "fields": [ + { + "name": "width", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Float", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "height", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Float", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "depth", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Float", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "AuctionLotImages", + "description": null, + "fields": [ + { + "name": "larger", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "Image", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "thumbnail", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "Image", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "ArtistBlurb", + "description": null, + "fields": [ + { + "name": "credit", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "text", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "partner_id", + "description": "The partner id of the partner who submitted the featured bio.", + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "ArtistCarousel", + "description": null, + "fields": [ + { + "name": "images", + "description": null, + "args": [], + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "Image", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "ArtistCounts", + "description": null, + "fields": [ + { + "name": "artworks", + "description": null, + "args": [ + { + "name": "format", + "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "label", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "FormattedNumber", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "follows", + "description": null, + "args": [ + { + "name": "format", + "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "label", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "FormattedNumber", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "for_sale_artworks", + "description": null, + "args": [ + { + "name": "format", + "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "label", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "FormattedNumber", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "partner_shows", + "description": null, + "args": [ + { + "name": "format", + "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "label", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "FormattedNumber", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "related_artists", + "description": null, + "args": [ + { + "name": "format", + "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "label", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "FormattedNumber", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "articles", + "description": null, + "args": [ + { + "name": "format", + "description": "Returns a `String` when format is specified. e.g.`'0,0.0000''`", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "label", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "SCALAR", + "name": "FormattedNumber", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "SCALAR", + "name": "FormattedNumber", + "description": "The `FormattedNumber` type represents a number that can optionally be returnedas a formatted String. It does not try to coerce the type.", + "fields": null, + "inputFields": null, + "interfaces": null, + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "Show", "description": null, "fields": [ { @@ -10602,9 +11457,80 @@ }, { "kind": "OBJECT", - "name": "PartnerArtist", - "description": null, + "name": "PartnerArtistConnection", + "description": "A connection to a list of items.", + "fields": [ + { + "name": "pageInfo", + "description": "Information to aid in pagination.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "PageInfo", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "edges", + "description": "A list of edges.", + "args": [], + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "PartnerArtistEdge", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "PartnerArtistEdge", + "description": "An edge in a connection.", "fields": [ + { + "name": "node", + "description": "The item at the end of the edge", + "args": [], + "type": { + "kind": "OBJECT", + "name": "Partner", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "cursor", + "description": "A cursor for use in pagination", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "__id", "description": "A globally unique ID.", @@ -10816,6 +11742,145 @@ "enumValues": null, "possibleTypes": null }, + { + "kind": "OBJECT", + "name": "PartnerArtist", + "description": null, + "fields": [ + { + "name": "__id", + "description": "A globally unique ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "id", + "description": "A type-specific ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "artist", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "Artist", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "biography", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "counts", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "PartnerArtistCounts", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "is_display_on_partner_profile", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "is_represented_by", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "is_use_default_biography", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "partner", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "Partner", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "sortable_id", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, { "kind": "OBJECT", "name": "RelatedArtists", @@ -11639,6 +12704,18 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "live_url_if_open", + "description": "Returns a live auctions url if the sale is open and start time is after now", + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "profile", "description": null, @@ -13544,7 +14621,7 @@ "description": null, "fields": [ { - "name": "partner_artists", + "name": "partners", "description": null, "args": [ { @@ -13570,16 +14647,52 @@ } }, "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null } ], "type": { - "kind": "LIST", - "name": null, - "ofType": { - "kind": "OBJECT", - "name": "PartnerArtist", - "ofType": null - } + "kind": "OBJECT", + "name": "PartnerArtistConnection", + "ofType": null }, "isDeprecated": false, "deprecationReason": null @@ -14143,6 +15256,18 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "live_url_if_open", + "description": "Returns a live auctions url if the sale is open and start time is after now", + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "profile", "description": null, @@ -15988,6 +17113,18 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "live_url_if_open", + "description": "Returns a live auctions url if the sale is open and start time is after now", + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "profile", "description": null, @@ -18570,6 +19707,11 @@ "kind": "OBJECT", "name": "ArtworkFilterTag", "ofType": null + }, + { + "kind": "OBJECT", + "name": "ArtworkFilterGene", + "ofType": null } ] }, @@ -18704,6 +19846,137 @@ "enumValues": null, "possibleTypes": null }, + { + "kind": "OBJECT", + "name": "ArtworkFilterGene", + "description": null, + "fields": [ + { + "name": "__id", + "description": "A globally unique ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "id", + "description": "A type-specific ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "_id", + "description": "A type-specific Gravity Mongo Document ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "cached", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "description", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "name", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "href", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "image", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "Image", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "count", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, { "kind": "ENUM", "name": "SaleArtworkAggregation", @@ -22576,6 +23849,18 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "live_url_if_open", + "description": "Returns a live auctions url if the sale is open and start time is after now", + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "profile", "description": null, @@ -23933,6 +25218,18 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "followsAndSaves", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "FollowsAndSaves", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "invoice", "description": "An invoice", @@ -24157,8 +25454,8 @@ "name": "NotificationsFeedItemConnection", "ofType": null }, - "isDeprecated": false, - "deprecationReason": null + "isDeprecated": true, + "deprecationReason": "Prefer to use followed_artists_artwork_groups." }, { "name": "paddle_number", @@ -28160,21 +29457,220 @@ }, { "kind": "OBJECT", - "name": "FollowGene", + "name": "FollowGene", + "description": null, + "fields": [ + { + "name": "gene", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "Gene", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "__id", + "description": "A globally unique ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "id", + "description": "A type-specific ID.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "FollowsAndSaves", "description": null, "fields": [ { - "name": "gene", - "description": null, + "name": "bundledArtworksByArtist", + "description": "A list of published artworks by followed artists (grouped by date and artists).", + "args": [ + { + "name": "sort", + "description": null, + "type": { + "kind": "ENUM", + "name": "ArtworkSorts", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "FollowedArtistsArtworksGroupConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "FollowedArtistsArtworksGroupConnection", + "description": "A connection to a list of items.", + "fields": [ + { + "name": "pageInfo", + "description": "Information to aid in pagination.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "PageInfo", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "edges", + "description": "A list of edges.", + "args": [], + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "FollowedArtistsArtworksGroupEdge", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "FollowedArtistsArtworksGroupEdge", + "description": "An edge in a connection.", + "fields": [ + { + "name": "node", + "description": "The item at the end of the edge", "args": [], "type": { "kind": "OBJECT", - "name": "Gene", + "name": "FollowedArtistsArtworksGroup", "ofType": null }, "isDeprecated": false, "deprecationReason": null }, + { + "name": "cursor", + "description": "A cursor for use in pagination", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "FollowedArtistsArtworksGroup", + "description": null, + "fields": [ { "name": "__id", "description": "A globally unique ID.", @@ -28192,24 +29688,66 @@ "deprecationReason": null }, { - "name": "id", - "description": "A type-specific ID.", + "name": "artworks", + "description": "List of artworks in this group.", "args": [], "type": { - "kind": "NON_NULL", + "kind": "LIST", "name": null, "ofType": { - "kind": "SCALAR", - "name": "String", + "kind": "OBJECT", + "name": "Artwork", "ofType": null } }, "isDeprecated": false, "deprecationReason": null + }, + { + "name": "artists", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "summary", + "description": null, + "args": [], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "image", + "description": null, + "args": [], + "type": { + "kind": "OBJECT", + "name": "Image", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null } ], "inputFields": null, - "interfaces": [], + "interfaces": [ + { + "kind": "INTERFACE", + "name": "Node", + "ofType": null + } + ], "enumValues": null, "possibleTypes": null }, @@ -28982,6 +30520,69 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "auctionResults", + "description": null, + "args": [ + { + "name": "sort", + "description": null, + "type": { + "kind": "ENUM", + "name": "AuctionResultSorts", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "AuctionResultConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "bio", "description": null, @@ -29086,6 +30687,22 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "collections", + "description": null, + "args": [], + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "contemporary", "description": null, @@ -29413,6 +31030,83 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "partners", + "description": null, + "args": [ + { + "name": "represented_by", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "partner_category", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "PartnerArtistConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "partner_artists", "description": null, @@ -32905,6 +34599,69 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "auctionResults", + "description": null, + "args": [ + { + "name": "sort", + "description": null, + "type": { + "kind": "ENUM", + "name": "AuctionResultSorts", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "AuctionResultConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "bio", "description": null, @@ -33009,6 +34766,22 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "collections", + "description": null, + "args": [], + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "contemporary", "description": null, @@ -33336,6 +35109,83 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "partners", + "description": null, + "args": [ + { + "name": "represented_by", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "partner_category", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "PartnerArtistConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "partner_artists", "description": null, @@ -35774,6 +37624,60 @@ "enumValues": null, "possibleTypes": null }, + { + "kind": "OBJECT", + "name": "Services", + "description": null, + "fields": [ + { + "name": "convection", + "description": null, + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "Convection", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "Convection", + "description": null, + "fields": [ + { + "name": "geminiTemplateKey", + "description": null, + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, { "kind": "OBJECT", "name": "Status", @@ -38196,6 +40100,18 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "services", + "description": "The schema for difference microservice settings", + "args": [], + "type": { + "kind": "OBJECT", + "name": "Services", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "show", "description": "A Show", @@ -39341,26 +41257,6 @@ }, "defaultValue": null }, - { - "name": "price_range_min", - "description": "The minimum price collector has selected", - "type": { - "kind": "SCALAR", - "name": "Int", - "ofType": null - }, - "defaultValue": null - }, - { - "name": "price_range_max", - "description": "The maximum price collector has selected", - "type": { - "kind": "SCALAR", - "name": "Int", - "ofType": null - }, - "defaultValue": null - }, { "name": "clientMutationId", "description": null, diff --git a/externals/metaphysics b/externals/metaphysics index 02662f235f..19528caf9a 160000 --- a/externals/metaphysics +++ b/externals/metaphysics @@ -1 +1 @@ -Subproject commit 02662f235f6fbc8b62565514fa7e1ee18f4880df +Subproject commit 19528caf9a69e04de9e05b2025717737d8b25036 diff --git a/src/Components/ArtworkFilter/Headline.tsx b/src/Components/ArtworkFilter/Headline.tsx index 5f79496f2b..742df92506 100644 --- a/src/Components/ArtworkFilter/Headline.tsx +++ b/src/Components/ArtworkFilter/Headline.tsx @@ -33,7 +33,6 @@ export class Headline extends React.Component { medium() { const { medium, facet } = this.props - if (medium && medium !== "*") { return this.getCountName("medium", medium) } @@ -87,6 +86,9 @@ export default createFragmentContainer( ... on ArtworkFilterTag { name } + ... on ArtworkFilterGene { + name + } } ` ) diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/Artworks.tsx index 90dac6f4c2..6cac9ba15c 100644 --- a/src/Components/Gene/Artworks.tsx +++ b/src/Components/Gene/Artworks.tsx @@ -29,7 +29,7 @@ interface Props extends RelayProps, Filters { onDropdownSelected: (slice: string, value: string) => void } -interface State { +interface State extends Filters { loading: boolean } @@ -56,8 +56,11 @@ const SpinnerContainer = styled.div` ` export class Artworks extends React.Component { - state = { - loading: false, + constructor(props: Props) { + super(props) + this.state = { + loading: false, + } } renderDropdown() { @@ -66,7 +69,7 @@ export class Artworks extends React.Component { ) @@ -92,7 +95,7 @@ export class Artworks extends React.Component { price_range={this.props.price_range} dimension_range={this.props.dimension_range} for_sale={this.props.for_sale} - facet={this.props.gene} + facet={this.props.gene.filtered_artworks.facet} aggregations={this.props.gene.filtered_artworks.aggregations} /> @@ -148,8 +151,13 @@ export default createPaginationContainer( sort: $sort ) { ...TotalCount_filter_artworks + aggregations { slice + counts { + name + id + } ...Dropdown_aggregation } artworks: artworks_connection(first: $count, after: $cursor) @connection(key: "Artworks_artworks") { @@ -164,6 +172,9 @@ export default createPaginationContainer( } ...ArtworkGrid_artworks } + facet { + ...Headline_facet + } } } `, @@ -227,10 +238,15 @@ interface RelayProps { filtered_artworks: { aggregations: Array<{ slice: string + counts: { + name: string | null + id: string | null + } }> artworks: { edges: Array<{}> } + facet: any } } } diff --git a/src/Components/Gene/NewContents.tsx b/src/Components/Gene/NewContents.tsx index e9ae0b7dd8..b612489689 100644 --- a/src/Components/Gene/NewContents.tsx +++ b/src/Components/Gene/NewContents.tsx @@ -67,6 +67,7 @@ class GeneNewContents extends React.Component { renderArtworks() { const { geneID, relayEnvironment } = this.props + const { for_sale, medium, price_range, dimension_range } = this.state return ( { variables={{ geneID, ...this.state }} render={({ props }) => { if (props) { - return + return } else { return null } diff --git a/src/Components/__stories__/Gene.story.tsx b/src/Components/__stories__/Gene.story.tsx index f49dcd84be..40a282574e 100644 --- a/src/Components/__stories__/Gene.story.tsx +++ b/src/Components/__stories__/Gene.story.tsx @@ -91,7 +91,7 @@ storiesOf("Components/Pages/Gene", module) .add("Integration - Minimalism", () => { return (
- < ContextProvider currentUser={{id: "matt-z", name: "Matt", accessToken: "REPLACE_ME"}}> + < ContextProvider currentUser={{id: "matt-z", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}>
From 60a18103237da3c6329054682a5fb0e8039ce73e Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Tue, 12 Dec 2017 13:58:03 -0500 Subject: [PATCH 04/12] wip- artwork sorting working --- src/Components/BorderedPulldown.tsx | 5 +++-- src/Components/Gene/Artworks.tsx | 5 ++++- src/Components/Gene/NewContents.tsx | 17 ++++++++++++++--- 3 files changed, 21 insertions(+), 6 deletions(-) diff --git a/src/Components/BorderedPulldown.tsx b/src/Components/BorderedPulldown.tsx index 3146170b53..2d200801e6 100644 --- a/src/Components/BorderedPulldown.tsx +++ b/src/Components/BorderedPulldown.tsx @@ -10,6 +10,7 @@ interface Props extends React.HTMLProps { options: any defaultValue: string onChange?: any + selectedName?: string } interface State { @@ -38,7 +39,7 @@ export class BorderedPulldown extends React.Component { } render() { - const { options, defaultValue } = this.props + const { options, defaultValue, selectedName } = this.props const optionEls = options.map(option => { return ( @@ -48,7 +49,7 @@ export class BorderedPulldown extends React.Component { ) }) - const displayValue = (this.state.selected && this.state.selected.name) || defaultValue + const displayValue = (this.state.selected && this.state.selected.name) || selectedName || defaultValue let pulldownStyles = {} if (this.state.isHovered) { diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/Artworks.tsx index 6cac9ba15c..a1d7bae83d 100644 --- a/src/Components/Gene/Artworks.tsx +++ b/src/Components/Gene/Artworks.tsx @@ -27,6 +27,8 @@ interface Filters { interface Props extends RelayProps, Filters { relay?: RelayPaginationProp onDropdownSelected: (slice: string, value: string) => void + onSortSelected: (sort: string) => void + sort?: string } interface State extends Filters { @@ -86,6 +88,7 @@ export class Artworks extends React.Component { { val: "-year", name: "Artwork Year (desc.)" }, { val: "year", name: "Artwork Year (asc.)" }, ] + const selectedSort = pulldownOptions.find((sort) => sort.val === this.props.sort) return (
@@ -100,7 +103,7 @@ export class Artworks extends React.Component { />
- null} /> + { @@ -31,6 +33,7 @@ class GeneNewContents extends React.Component { price_range: "*", dimension_range: "*", mode: props.mode, + sort: "-partner_updated_at", } } @@ -41,6 +44,13 @@ class GeneNewContents extends React.Component { }) } + onSortSelect(sortEl) { + this.setState({ + sort: sortEl.val, + mode: "artworks", + }) + } + renderArtists() { const { geneID, relayEnvironment } = this.props return ( @@ -67,23 +77,24 @@ class GeneNewContents extends React.Component { renderArtworks() { const { geneID, relayEnvironment } = this.props - const { for_sale, medium, price_range, dimension_range } = this.state + const { for_sale, medium, price_range, dimension_range, sort } = this.state return ( { if (props) { - return + return } else { return null } From ba26a475df6a4cb437fc6d5ffd6735b63b6d7cfd Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Tue, 12 Dec 2017 14:26:20 -0500 Subject: [PATCH 05/12] wip- artwork for sale toggle working --- .../ArtworkFilter/ForSaleCheckbox.tsx | 8 ++++---- src/Components/Checkbox.tsx | 2 +- src/Components/Gene/Artworks.tsx | 3 ++- src/Components/Gene/NewContents.tsx | 17 +++++++++++++++-- 4 files changed, 22 insertions(+), 8 deletions(-) diff --git a/src/Components/ArtworkFilter/ForSaleCheckbox.tsx b/src/Components/ArtworkFilter/ForSaleCheckbox.tsx index bdf3029c69..d52b681cd1 100644 --- a/src/Components/ArtworkFilter/ForSaleCheckbox.tsx +++ b/src/Components/ArtworkFilter/ForSaleCheckbox.tsx @@ -7,7 +7,7 @@ import colors from "../../Assets/Colors" import { primary } from "../../Assets/Fonts" interface Props extends React.HTMLProps { - onClick?: any + onChange?: any } interface State { @@ -23,15 +23,15 @@ export class ForSaleCheckbox extends React.Component { this.setState({ isChecked: !this.state.isChecked, }) - this.props.onClick() + this.props.onChange() } render() { const { isChecked } = this.state - + const { checked } = this.props return (
this.onClick()}> - +
) diff --git a/src/Components/Checkbox.tsx b/src/Components/Checkbox.tsx index d4b864e3e5..6b3e9e5d9c 100644 --- a/src/Components/Checkbox.tsx +++ b/src/Components/Checkbox.tsx @@ -17,7 +17,7 @@ export class Checkbox extends React.Component { return (
- + null} type="checkbox" checked={checked} />
) diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/Artworks.tsx index a1d7bae83d..297df24058 100644 --- a/src/Components/Gene/Artworks.tsx +++ b/src/Components/Gene/Artworks.tsx @@ -28,6 +28,7 @@ interface Props extends RelayProps, Filters { relay?: RelayPaginationProp onDropdownSelected: (slice: string, value: string) => void onSortSelected: (sort: string) => void + onForSaleToggleSelected: () => void sort?: string } @@ -79,7 +80,7 @@ export class Artworks extends React.Component { } renderForSaleToggle() { - return null} /> + return } renderArtworks() { diff --git a/src/Components/Gene/NewContents.tsx b/src/Components/Gene/NewContents.tsx index 2931ca13a0..5688e1ef85 100644 --- a/src/Components/Gene/NewContents.tsx +++ b/src/Components/Gene/NewContents.tsx @@ -44,6 +44,18 @@ class GeneNewContents extends React.Component { }) } + onForSaleToggleSelect() { + if (this.state.for_sale) { + this.setState({ + for_sale: null + }) + } else { + this.setState({ + for_sale: true + }) + } + } + onSortSelect(sortEl) { this.setState({ sort: sortEl.val, @@ -85,16 +97,17 @@ class GeneNewContents extends React.Component { query NewContentsArtworksQuery($geneID: String!, $medium: String $price_range: String $sort: String + $for_sale: Boolean $dimension_range: String) { gene(id: $geneID) { - ...Artworks_gene @arguments(medium: $medium, price_range: $price_range, dimension_range: $dimension_range, sort: $sort) + ...Artworks_gene @arguments(for_sale: $for_sale, medium: $medium, price_range: $price_range, dimension_range: $dimension_range, sort: $sort) } } `} variables={{ geneID, ...this.state }} render={({ props }) => { if (props) { - return + return } else { return null } From 3cdac439239e487bda59139706784d456a51e9f6 Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Tue, 12 Dec 2017 15:58:09 -0500 Subject: [PATCH 06/12] wip- artist mode from artworks --- src/Components/Gene/Artworks.tsx | 29 +++++++++++++++++ src/Components/Gene/NewContents.tsx | 49 +++++++++++++++++++++++------ 2 files changed, 68 insertions(+), 10 deletions(-) diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/Artworks.tsx index 297df24058..f9dc4cede0 100644 --- a/src/Components/Gene/Artworks.tsx +++ b/src/Components/Gene/Artworks.tsx @@ -3,6 +3,8 @@ import { ConnectionData } from "react-relay" import { createPaginationContainer, graphql, RelayPaginationProp } from "react-relay" import styled from "styled-components" +import { ButtonState } from "../Buttons/Default" +import Button from "../Buttons/Ghost" import Spinner from "../Spinner" import Dropdown from "../ArtworkFilter/Dropdown" @@ -29,6 +31,7 @@ interface Props extends RelayProps, Filters { onDropdownSelected: (slice: string, value: string) => void onSortSelected: (sort: string) => void onForSaleToggleSelected: () => void + onArtistModeToggleSelected: () => void sort?: string } @@ -58,6 +61,14 @@ const SpinnerContainer = styled.div` position: relative; ` +const ArtistFilterButtons = styled.div` + margin-right: 10px; + button { + height: 52px; + padding: 16px; + } +` + export class Artworks extends React.Component { constructor(props: Props) { super(props) @@ -79,6 +90,23 @@ export class Artworks extends React.Component { }) } + + + renderArtistsModeToggle() { + return ( + + By Artists: + + By Work: + + ) + } + renderForSaleToggle() { return } @@ -121,6 +149,7 @@ export class Artworks extends React.Component { return (
+ {this.renderArtistsModeToggle()} {this.renderForSaleToggle()} {this.renderDropdown()} diff --git a/src/Components/Gene/NewContents.tsx b/src/Components/Gene/NewContents.tsx index 5688e1ef85..180451df5c 100644 --- a/src/Components/Gene/NewContents.tsx +++ b/src/Components/Gene/NewContents.tsx @@ -47,11 +47,11 @@ class GeneNewContents extends React.Component { onForSaleToggleSelect() { if (this.state.for_sale) { this.setState({ - for_sale: null + for_sale: null, }) } else { this.setState({ - for_sale: true + for_sale: true, }) } } @@ -59,7 +59,13 @@ class GeneNewContents extends React.Component { onSortSelect(sortEl) { this.setState({ sort: sortEl.val, - mode: "artworks", + mode: "artworks", + }) + } + + onArtistModeSelect() { + this.setState({ + mode: "artists", }) } @@ -94,20 +100,43 @@ class GeneNewContents extends React.Component { { if (props) { - return + return ( + + ) } else { return null } From 8c914175f4e24549d5c40d4fd85740563653e5d6 Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Wed, 13 Dec 2017 17:46:02 -0500 Subject: [PATCH 07/12] wip- artwork load more works! --- data/schema.graphql | 66 +++- data/schema.json | 311 ++++++++++++++++-- externals/metaphysics | 2 +- package.json | 2 +- src/Components/ArtworkFilter/index.tsx | 2 +- src/Components/ArtworkGrid.tsx | 18 +- src/Components/Gene/Artworks.tsx | 104 +----- src/Components/Gene/ArtworksContent.tsx | 117 +++++++ src/Components/Gene/Contents.tsx | 3 +- src/Components/Gene/NewContents.tsx | 1 - .../Onboarding/Steps/Genes/SuggestedGenes.tsx | 6 +- .../__stories__/ArtworkGrid.story.tsx | 4 +- src/Components/__stories__/Gene.story.tsx | 2 +- 13 files changed, 490 insertions(+), 148 deletions(-) create mode 100644 src/Components/Gene/ArtworksContent.tsx diff --git a/data/schema.graphql b/data/schema.graphql index 45f5f154d8..32305e5a2a 100644 --- a/data/schema.graphql +++ b/data/schema.graphql @@ -2247,10 +2247,13 @@ type FeaturedLinkItem { title: String } -type FilterArtworks { +type FilterArtworks implements Node { + # The ID of the object. + __id: ID! + # Returns aggregation counts for the given filter query. aggregations: [ArtworksAggregationResults] - artworks_connection(after: String, first: Int, before: String, last: Int): ArtworkConnection @deprecated(reason: "Favour artwork connections that take filter arguments.") + artworks_connection(sort: String, after: String, first: Int, before: String, last: Int): ArtworkConnection @deprecated(reason: "Favour artwork connections that take filter arguments.") counts: FilterArtworksCounts followed_artists_total: Int @deprecated(reason: "Favor `favor counts.followed_artists`") @@ -2526,6 +2529,16 @@ type Gene implements Node { is_published: Boolean mode: String name: String + + # A list of genes similar to the specified gene + similar( + # Array of gene ids (not slugs) to exclude, may result in all genes being excluded. + exclude_gene_ids: [String] + after: String + first: Int + before: String + last: Int + ): GeneConnection trending_artists(sample: Int): [Artist] } @@ -2551,6 +2564,24 @@ type GeneArtworksEdge { cursor: String! } +# A connection to a list of items. +type GeneConnection { + # Information to aid in pagination. + pageInfo: PageInfo! + + # A list of edges. + edges: [GeneEdge] +} + +# An edge in a connection. +type GeneEdge { + # The item at the end of the edge + node: Gene + + # A cursor for use in pagination + cursor: String! +} + type GeneFamily { id: String! name: String! @@ -2660,6 +2691,16 @@ type GeneItem implements Node { is_published: Boolean mode: String name: String + + # A list of genes similar to the specified gene + similar( + # Array of gene ids (not slugs) to exclude, may result in all genes being excluded. + exclude_gene_ids: [String] + after: String + first: Int + before: String + last: Int + ): GeneConnection trending_artists(sample: Int): [Artist] } @@ -3107,6 +3148,16 @@ type HomePageModuleContextGene implements Node { is_published: Boolean mode: String name: String + + # A list of genes similar to the specified gene + similar( + # Array of gene ids (not slugs) to exclude, may result in all genes being excluded. + exclude_gene_ids: [String] + after: String + first: Int + before: String + last: Int + ): GeneConnection trending_artists(sample: Int): [Artist] } @@ -4302,7 +4353,7 @@ type Query { ): Gene # List of curated genes with custom images - suggested_genes: [SuggestedGene] + suggested_genes: [Gene] # A list of Gene Families gene_families(after: String, first: Int, before: String, last: Int): GeneFamilyConnection @@ -5192,13 +5243,6 @@ enum SubmissionStateAggregation { REJECTED } -type SuggestedGene { - id: String - image_url: String - _id: String - name: String -} - type Tag { # A globally unique ID. __id: ID! @@ -5548,7 +5592,7 @@ type Viewer { ): Gene # List of curated genes with custom images - suggested_genes: [SuggestedGene] + suggested_genes: [Gene] # A list of Gene Families gene_families(after: String, first: Int, before: String, last: Int): GeneFamilyConnection diff --git a/data/schema.json b/data/schema.json index dbf7d220c7..9b7b8dc405 100644 --- a/data/schema.json +++ b/data/schema.json @@ -1080,7 +1080,7 @@ "name": null, "ofType": { "kind": "OBJECT", - "name": "SuggestedGene", + "name": "Gene", "ofType": null } }, @@ -2704,6 +2704,11 @@ "name": "Collection", "ofType": null }, + { + "kind": "OBJECT", + "name": "FilterArtworks", + "ofType": null + }, { "kind": "OBJECT", "name": "Gene", @@ -19423,6 +19428,22 @@ "name": "FilterArtworks", "description": null, "fields": [ + { + "name": "__id", + "description": "The ID of the object.", + "args": [], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + } + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "aggregations", "description": "Returns aggregation counts for the given filter query.", @@ -19443,6 +19464,16 @@ "name": "artworks_connection", "description": null, "args": [ + { + "name": "sort", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, { "name": "after", "description": null, @@ -19574,7 +19605,13 @@ } ], "inputFields": null, - "interfaces": [], + "interfaces": [ + { + "kind": "INTERFACE", + "name": "Node", + "ofType": null + } + ], "enumValues": null, "possibleTypes": null }, @@ -21051,6 +21088,73 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "similar", + "description": "A list of genes similar to the specified gene", + "args": [ + { + "name": "exclude_gene_ids", + "description": "Array of gene ids (not slugs) to exclude, may result in all genes being excluded.", + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "GeneConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "trending_artists", "description": null, @@ -21202,53 +21306,76 @@ }, { "kind": "OBJECT", - "name": "SuggestedGene", - "description": null, + "name": "GeneConnection", + "description": "A connection to a list of items.", "fields": [ { - "name": "id", - "description": null, + "name": "pageInfo", + "description": "Information to aid in pagination.", "args": [], "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "PageInfo", + "ofType": null + } }, "isDeprecated": false, "deprecationReason": null }, { - "name": "image_url", - "description": null, + "name": "edges", + "description": "A list of edges.", "args": [], "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null + "kind": "LIST", + "name": null, + "ofType": { + "kind": "OBJECT", + "name": "GeneEdge", + "ofType": null + } }, "isDeprecated": false, "deprecationReason": null - }, + } + ], + "inputFields": null, + "interfaces": [], + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "GeneEdge", + "description": "An edge in a connection.", + "fields": [ { - "name": "_id", - "description": null, + "name": "node", + "description": "The item at the end of the edge", "args": [], "type": { - "kind": "SCALAR", - "name": "String", + "kind": "OBJECT", + "name": "Gene", "ofType": null }, "isDeprecated": false, "deprecationReason": null }, { - "name": "name", - "description": null, + "name": "cursor", + "description": "A cursor for use in pagination", "args": [], "type": { - "kind": "SCALAR", - "name": "String", - "ofType": null + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } }, "isDeprecated": false, "deprecationReason": null @@ -23253,6 +23380,73 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "similar", + "description": "A list of genes similar to the specified gene", + "args": [ + { + "name": "exclude_gene_ids", + "description": "Array of gene ids (not slugs) to exclude, may result in all genes being excluded.", + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "GeneConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "trending_artists", "description": null, @@ -33689,6 +33883,73 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "similar", + "description": "A list of genes similar to the specified gene", + "args": [ + { + "name": "exclude_gene_ids", + "description": "Array of gene ids (not slugs) to exclude, may result in all genes being excluded.", + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "after", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "first", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "before", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "last", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "GeneConnection", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "trending_artists", "description": null, @@ -39039,7 +39300,7 @@ "name": null, "ofType": { "kind": "OBJECT", - "name": "SuggestedGene", + "name": "Gene", "ofType": null } }, diff --git a/externals/metaphysics b/externals/metaphysics index 19528caf9a..a72c32d693 160000 --- a/externals/metaphysics +++ b/externals/metaphysics @@ -1 +1 @@ -Subproject commit 19528caf9a69e04de9e05b2025717737d8b25036 +Subproject commit a72c32d6935006c80993db5e8748736dcb97079c diff --git a/package.json b/package.json index 50e7ff4584..a58112bb34 100644 --- a/package.json +++ b/package.json @@ -22,7 +22,7 @@ "test:watch": "jest --watch --runInBand", "storybook": "node verify-node-version.js && concurrently --kill-others 'yarn relay --watch' 'env GRAPHQL_NO_NAME_WARNING=true start-storybook -p 9001'", "deploy-storybook": "yarn relay && NODE_ENV=production storybook-to-ghpages", - "sync-schema": "cd externals/metaphysics && git fetch && git checkout origin/master && yarn install && npm run dump-schema -- ../../data", + "sync-schema": "cd externals/metaphysics && git fetch && git checkout origin/pagination_fuckery && yarn install && npm run dump-schema -- ../../data", "sync-colors": "cd externals/elan && git fetch && git checkout origin/master && cp components/lib/variables/colors.json ../../data", "lint": "tslint -c tslint.json --project tsconfig.json", "type-check": "tsc --noEmit --pretty", diff --git a/src/Components/ArtworkFilter/index.tsx b/src/Components/ArtworkFilter/index.tsx index 31c0989881..3f1d0af9c1 100644 --- a/src/Components/ArtworkFilter/index.tsx +++ b/src/Components/ArtworkFilter/index.tsx @@ -186,12 +186,12 @@ export default createPaginationContainer( ...TotalCount_filter_artworks artworks: artworks_connection(first: $count, after: $cursor) @connection(key: "ArtworkFilter_filter_artworks") { - ...ArtworkGrid_artworks pageInfo { hasNextPage endCursor } edges { + ...ArtworkGrid_artworks node { __id } diff --git a/src/Components/ArtworkGrid.tsx b/src/Components/ArtworkGrid.tsx index c360e84ce9..9dabcc12f7 100644 --- a/src/Components/ArtworkGrid.tsx +++ b/src/Components/ArtworkGrid.tsx @@ -51,7 +51,7 @@ export class ArtworkGrid extends React.Component { sectionedArtworks() { const sectionedArtworks: ArtworkRelayProps[][] = [] const sectionRatioSums = [] - const artworks = this.props.artworks ? this.props.artworks.edges : [] + const artworks = this.props.artworks ? this.props.artworks : [] for (let i = 0; i < this.props.columnCount; i++) { sectionedArtworks.push([]) @@ -144,16 +144,16 @@ const StyledGrid = styled(ArtworkGrid) ` export default createFragmentContainer( StyledGrid, graphql` - fragment ArtworkGrid_artworks on ArtworkConnection { - edges { - node { - __id - image { - aspect_ratio - } - ...GridItem_artwork + fragment ArtworkGrid_artworks on ArtworkEdge @relay(plural: true) { + + node { + __id + image { + aspect_ratio } + ...GridItem_artwork } + } ` ) diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/Artworks.tsx index f9dc4cede0..68dbea3e97 100644 --- a/src/Components/Gene/Artworks.tsx +++ b/src/Components/Gene/Artworks.tsx @@ -1,11 +1,9 @@ import * as React from "react" -import { ConnectionData } from "react-relay" -import { createPaginationContainer, graphql, RelayPaginationProp } from "react-relay" +import { createFragmentContainer, graphql, RelayPaginationProp } from "react-relay" import styled from "styled-components" import { ButtonState } from "../Buttons/Default" import Button from "../Buttons/Ghost" -import Spinner from "../Spinner" import Dropdown from "../ArtworkFilter/Dropdown" import ForSaleCheckbox from "../ArtworkFilter/ForSaleCheckbox" @@ -15,9 +13,7 @@ import TotalCount from "../ArtworkFilter/TotalCount" import BorderedPulldown from "../BorderedPulldown" -import ArtworkGrid from "../ArtworkGrid" - -const PageSize = 10 +import ArtworksContent from "./ArtworksContent" interface Filters { for_sale?: boolean @@ -55,12 +51,6 @@ const SubFilterBar = styled.div` align-items: center; ` -const SpinnerContainer = styled.div` - width: 100%; - height: 100px; - position: relative; -` - const ArtistFilterButtons = styled.div` margin-right: 10px; button { @@ -78,6 +68,7 @@ export class Artworks extends React.Component { } renderDropdown() { + debugger return this.props.gene.filtered_artworks.aggregations.map(aggregation => { return ( { }) } - - renderArtistsModeToggle() { return ( @@ -111,6 +100,8 @@ export class Artworks extends React.Component { return } + + renderArtworks() { const pulldownOptions = [ { val: "-partner_updated_at", name: "Recently Updated" }, @@ -134,13 +125,7 @@ export class Artworks extends React.Component {
- null} - /> - {this.state.loading ? : ""} + ) } @@ -159,15 +144,12 @@ export class Artworks extends React.Component { } } -export default createPaginationContainer( +export default createFragmentContainer( Artworks, { gene: graphql.experimental` fragment Artworks_gene on Gene @argumentDefinitions( - count: { type: "Int", defaultValue: 10 } - cursor: { type: "String", defaultValue: "" } - sort: { type: "String", defaultValue: "-partner_updated_at" } for_sale: { type: "Boolean" } medium: { type: "String", defaultValue: "*" } aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] } @@ -176,15 +158,14 @@ export default createPaginationContainer( ) { filtered_artworks( aggregations: $aggregations - size: $count for_sale: $for_sale medium: $medium price_range: $price_range dimension_range: $dimension_range - sort: $sort + size: 0 ) { ...TotalCount_filter_artworks - + ...ArtworksContent_filtered_artworks aggregations { slice counts { @@ -193,18 +174,7 @@ export default createPaginationContainer( } ...Dropdown_aggregation } - artworks: artworks_connection(first: $count, after: $cursor) @connection(key: "Artworks_artworks") { - pageInfo { - hasNextPage - endCursor - } - edges { - node { - __id - } - } - ...ArtworkGrid_artworks - } + facet { ...Headline_facet } @@ -212,57 +182,6 @@ export default createPaginationContainer( } `, }, - { - direction: "forward", - getConnectionFromProps(props) { - return props.gene.filtered_artworks.artworks as ConnectionData - }, - getFragmentVariables(prevVars, totalCount) { - return { - ...prevVars, - count: totalCount, - } - }, - getVariables(props, { count, cursor }, fragmentVariables) { - return { - // in most cases, for variables other than connection filters like - // `first`, `after`, etc. you may want to use the previous values. - ...fragmentVariables, - count, - cursor, - geneNodeID: props.gene.__id, - } - }, - query: graphql.experimental` - query ArtworksQuery( - $geneNodeID: ID! - $count: Int! - $cursor: String - $showArtists: Boolean - $sort: String - $for_sale: Boolean - $medium: String - $aggregations: [ArtworkAggregation] - $price_range: String - $dimension_range: String - ) { - node(__id: $geneNodeID) { - ...Artworks_gene - @arguments( - count: $count - cursor: $cursor - showArtists: $showArtists - sort: $sort - for_sale: $for_sale - medium: $medium - aggregations: $aggregations - price_range: $price_range - dimension_range: $dimension_range - ) - } - } - `, - } ) interface RelayProps { @@ -276,9 +195,6 @@ interface RelayProps { id: string | null } }> - artworks: { - edges: Array<{}> - } facet: any } } diff --git a/src/Components/Gene/ArtworksContent.tsx b/src/Components/Gene/ArtworksContent.tsx new file mode 100644 index 0000000000..49eda067fe --- /dev/null +++ b/src/Components/Gene/ArtworksContent.tsx @@ -0,0 +1,117 @@ +import * as React from "react" +import {ConnectionData, createPaginationContainer,graphql, RelayPaginationProp} from "react-relay" +import styled from "styled-components" +import ArtworkGrid from "../ArtworkGrid" +import Spinner from "../Spinner" + +interface Props extends RelayProps { + relay?: RelayPaginationProp +} + +const SpinnerContainer = styled.div` + width: 100%; + height: 100px; + position: relative; +` + +const PageSize = 10 + +export class ArtworksContent extends React.Component { + loadMoreArtworks() { + const hasMore = this.props.filtered_artworks.artworks.pageInfo.hasNextPage + if (hasMore && !this.props.relay.isLoading()) { + this.props.relay.loadMore(PageSize, (e) => { + console.log(e) + }) + } + } + + render() { + return ( +
+ this.loadMoreArtworks()} + /> + {this.props.relay.isLoading() ? : ""} +
+ ) + } +} + +export default createPaginationContainer( + ArtworksContent, + { + filtered_artworks: graphql.experimental` + fragment ArtworksContent_filtered_artworks on FilterArtworks + @argumentDefinitions( + count: { type: "Int", defaultValue: 10 } + cursor: { type: "String", defaultValue: "" } + ) { + __id + artworks: artworks_connection(first: $count, after: $cursor, sort: $sort) @connection(key: "ArtworksContent_filtered_artworks") { + pageInfo { + hasNextPage + endCursor + } + edges { + ...ArtworkGrid_artworks + node { + __id + } + } + } + } + `, + }, + { + direction: "forward", + getConnectionFromProps(props) { + return props.filtered_artworks.artworks as ConnectionData + }, + getFragmentVariables(prevVars, totalCount) { + return { + ...prevVars, + count: totalCount, + } + }, + getVariables(props, { count, cursor }, fragmentVariables) { + return { + // in most cases, for variables other than connection filters like + // `first`, `after`, etc. you may want to use the previous values. + ...fragmentVariables, + count, + cursor, + filteredArtworksNodeID: props.filtered_artworks.__id, + } + }, + query: graphql.experimental` + query ArtworksContentQuery( + $filteredArtworksNodeID: ID! + $count: Int! + $cursor: String + $sort: String + ) { + node(__id: $filteredArtworksNodeID) { + ...ArtworksContent_filtered_artworks @arguments( + count: $count, + cursor: $cursor, + ) + } + } + `, + } +) + +interface RelayProps { + filtered_artworks: { + artworks: { + edges: Array<{}> + pageInfo: { + hasNextPage: boolean + } + } + } +} diff --git a/src/Components/Gene/Contents.tsx b/src/Components/Gene/Contents.tsx index 97b222d13f..f03faabb7f 100644 --- a/src/Components/Gene/Contents.tsx +++ b/src/Components/Gene/Contents.tsx @@ -338,11 +338,12 @@ export default createPaginationContainer( endCursor } edges { + ...ArtworkGrid_artworks node { __id } } - ...ArtworkGrid_artworks + } } } diff --git a/src/Components/Gene/NewContents.tsx b/src/Components/Gene/NewContents.tsx index 180451df5c..8f95fa7e03 100644 --- a/src/Components/Gene/NewContents.tsx +++ b/src/Components/Gene/NewContents.tsx @@ -115,7 +115,6 @@ class GeneNewContents extends React.Component { medium: $medium price_range: $price_range dimension_range: $dimension_range - sort: $sort ) } } diff --git a/src/Components/Onboarding/Steps/Genes/SuggestedGenes.tsx b/src/Components/Onboarding/Steps/Genes/SuggestedGenes.tsx index a392b6d5e2..0ea3e41570 100644 --- a/src/Components/Onboarding/Steps/Genes/SuggestedGenes.tsx +++ b/src/Components/Onboarding/Steps/Genes/SuggestedGenes.tsx @@ -27,11 +27,13 @@ class SuggestedGenesContent extends React.Component { const SuggestedGenesContainer = createFragmentContainer( SuggestedGenesContent, graphql` - fragment SuggestedGenesContent_suggested_genes on SuggestedGene @relay(plural: true) { + fragment SuggestedGenesContent_suggested_genes on Gene @relay(plural: true) { id name _id - image_url + image { + url + } } ` ) diff --git a/src/Components/__stories__/ArtworkGrid.story.tsx b/src/Components/__stories__/ArtworkGrid.story.tsx index 00442f86ad..bd5789babc 100644 --- a/src/Components/__stories__/ArtworkGrid.story.tsx +++ b/src/Components/__stories__/ArtworkGrid.story.tsx @@ -13,7 +13,9 @@ function GridExample(props: { artistID: string; currentUser: User }) { query ArtworkGridQuery($artistID: String!) { artist(id: $artistID) { artworks: artworks_connection(first: 10) { - ...ArtworkGrid_artworks + edges { + ...ArtworkGrid_artworks + } } } } diff --git a/src/Components/__stories__/Gene.story.tsx b/src/Components/__stories__/Gene.story.tsx index 40a282574e..d52f038442 100644 --- a/src/Components/__stories__/Gene.story.tsx +++ b/src/Components/__stories__/Gene.story.tsx @@ -91,7 +91,7 @@ storiesOf("Components/Pages/Gene", module) .add("Integration - Minimalism", () => { return (
- < ContextProvider currentUser={{id: "matt-z", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> + < ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}>
From e46b6fda18c1f3a519bf1c127111d2caab5ee3e1 Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Thu, 14 Dec 2017 14:07:04 -0500 Subject: [PATCH 08/12] cleanup of gene --- externals/metaphysics | 2 +- package.json | 3 +- src/Components/ArtworkFilter/index.tsx | 5 +- src/Components/ArtworkGrid.tsx | 18 +- src/Components/Gene/Artists.tsx | 46 +- src/Components/Gene/Artworks.tsx | 1 - src/Components/Gene/ArtworksContent.tsx | 10 +- src/Components/Gene/Contents.tsx | 402 ------------------ src/Components/Gene/NewContents.tsx | 157 ------- src/Components/Gene/index.tsx | 167 +++++++- .../__stories__/ArtworkGrid.story.tsx | 4 +- src/Components/__stories__/Gene.story.tsx | 89 +--- 12 files changed, 199 insertions(+), 705 deletions(-) delete mode 100644 src/Components/Gene/Contents.tsx delete mode 100644 src/Components/Gene/NewContents.tsx diff --git a/externals/metaphysics b/externals/metaphysics index a72c32d693..40ef926133 160000 --- a/externals/metaphysics +++ b/externals/metaphysics @@ -1 +1 @@ -Subproject commit a72c32d6935006c80993db5e8748736dcb97079c +Subproject commit 40ef9261337abcc931ad36bdc5843d9ca51ec7fa diff --git a/package.json b/package.json index a58112bb34..b64a824f72 100644 --- a/package.json +++ b/package.json @@ -22,7 +22,8 @@ "test:watch": "jest --watch --runInBand", "storybook": "node verify-node-version.js && concurrently --kill-others 'yarn relay --watch' 'env GRAPHQL_NO_NAME_WARNING=true start-storybook -p 9001'", "deploy-storybook": "yarn relay && NODE_ENV=production storybook-to-ghpages", - "sync-schema": "cd externals/metaphysics && git fetch && git checkout origin/pagination_fuckery && yarn install && npm run dump-schema -- ../../data", + "sync-schema": "cd externals/metaphysics && git fetch && git checkout origin/master && yarn install && npm run dump-schema -- ../../data", + "sync-schema:localhost": "cd ../metaphysics && yarn dump-schema -- ../emission/data", "sync-colors": "cd externals/elan && git fetch && git checkout origin/master && cp components/lib/variables/colors.json ../../data", "lint": "tslint -c tslint.json --project tsconfig.json", "type-check": "tsc --noEmit --pretty", diff --git a/src/Components/ArtworkFilter/index.tsx b/src/Components/ArtworkFilter/index.tsx index 3f1d0af9c1..40fc89bea9 100644 --- a/src/Components/ArtworkFilter/index.tsx +++ b/src/Components/ArtworkFilter/index.tsx @@ -90,7 +90,7 @@ class ArtworkFilter extends React.Component { this.onSelect(count, slice)} + onSelected={(count, slice) => this.onSelect(count, slice)} /> )) const pulldownOptions = [ @@ -191,11 +191,12 @@ export default createPaginationContainer( endCursor } edges { - ...ArtworkGrid_artworks + node { __id } } + ...ArtworkGrid_artworks } facet { ...Headline_facet diff --git a/src/Components/ArtworkGrid.tsx b/src/Components/ArtworkGrid.tsx index 9dabcc12f7..c360e84ce9 100644 --- a/src/Components/ArtworkGrid.tsx +++ b/src/Components/ArtworkGrid.tsx @@ -51,7 +51,7 @@ export class ArtworkGrid extends React.Component { sectionedArtworks() { const sectionedArtworks: ArtworkRelayProps[][] = [] const sectionRatioSums = [] - const artworks = this.props.artworks ? this.props.artworks : [] + const artworks = this.props.artworks ? this.props.artworks.edges : [] for (let i = 0; i < this.props.columnCount; i++) { sectionedArtworks.push([]) @@ -144,16 +144,16 @@ const StyledGrid = styled(ArtworkGrid) ` export default createFragmentContainer( StyledGrid, graphql` - fragment ArtworkGrid_artworks on ArtworkEdge @relay(plural: true) { - - node { - __id - image { - aspect_ratio + fragment ArtworkGrid_artworks on ArtworkConnection { + edges { + node { + __id + image { + aspect_ratio + } + ...GridItem_artwork } - ...GridItem_artwork } - } ` ) diff --git a/src/Components/Gene/Artists.tsx b/src/Components/Gene/Artists.tsx index b7bfa51826..853245b4ad 100644 --- a/src/Components/Gene/Artists.tsx +++ b/src/Components/Gene/Artists.tsx @@ -51,20 +51,20 @@ const SpinnerContainer = styled.div` ` const ArtistFilterButtons = styled.div` -margin-right: 10px; -button { - height: 52px; - padding: 16px; -} + margin-right: 10px; + button { + height: 52px; + padding: 16px; + } ` const FilterBar = styled.div` -vertical-align: middle; -text-align: center; + vertical-align: middle; + text-align: center; -> div { - display: inline-block; -} + > div { + display: inline-block; + } ` export class Artists extends React.Component { @@ -113,7 +113,6 @@ export class Artists extends React.Component { }) } - render() { const artists = this.props.gene.artists @@ -129,15 +128,16 @@ export class Artists extends React.Component { return (
- - {this.renderArtistFilter()} - {this.renderArtistDropdown()} - - - {artistRows} - {this.state.loading ? : ""} - {artists && artists.pageInfo.hasNextPage && !this.state.loading && loadMoreButton} -
+ + {this.renderArtistFilter()} + {this.renderArtistDropdown()} + + + {artistRows} + {this.state.loading ? : ""} + {artists && artists.pageInfo.hasNextPage && !this.state.loading && loadMoreButton} + + ) } } @@ -147,7 +147,11 @@ export default createPaginationContainer( { gene: graphql.experimental` fragment Artists_gene on Gene - @argumentDefinitions(aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] }, count: { type: "Int", defaultValue: 10 }, cursor: { type: "String", defaultValue: "" }) { + @argumentDefinitions( + aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] } + count: { type: "Int", defaultValue: 10 } + cursor: { type: "String", defaultValue: "" } + ) { __id artists: artists_connection(first: $count, after: $cursor) @connection(key: "Artists_artists") { pageInfo { diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/Artworks.tsx index 68dbea3e97..33a966c27e 100644 --- a/src/Components/Gene/Artworks.tsx +++ b/src/Components/Gene/Artworks.tsx @@ -68,7 +68,6 @@ export class Artworks extends React.Component { } renderDropdown() { - debugger return this.props.gene.filtered_artworks.aggregations.map(aggregation => { return ( { loadMoreArtworks() { const hasMore = this.props.filtered_artworks.artworks.pageInfo.hasNextPage if (hasMore && !this.props.relay.isLoading()) { - this.props.relay.loadMore(PageSize, (e) => { - console.log(e) + this.props.relay.loadMore(PageSize, error => { + if (error) { + console.error(error) + } }) } } @@ -30,7 +32,7 @@ export class ArtworksContent extends React.Component { return (
this.loadMoreArtworks()} @@ -56,8 +58,8 @@ export default createPaginationContainer( hasNextPage endCursor } + ...ArtworkGrid_artworks edges { - ...ArtworkGrid_artworks node { __id } diff --git a/src/Components/Gene/Contents.tsx b/src/Components/Gene/Contents.tsx deleted file mode 100644 index f03faabb7f..0000000000 --- a/src/Components/Gene/Contents.tsx +++ /dev/null @@ -1,402 +0,0 @@ -import React from "react" -import { ConnectionData, createPaginationContainer, graphql, RelayPaginationProp } from "react-relay" -import styled from "styled-components" - -import { addUrlProps, UrlQueryParamTypes } from "react-url-query" - -import Dropdown from "../ArtworkFilter/Dropdown" -import ForSaleCheckbox from "../ArtworkFilter/ForSaleCheckbox" -import Headline from "../ArtworkFilter/Headline" -import TotalCount from "../ArtworkFilter/TotalCount" - -import BorderedPulldown from "../BorderedPulldown" -import { ButtonState } from "../Buttons/Default" -import Button from "../Buttons/Ghost" -import Spinner from "../Spinner" - -import ArtworkGrid from "../ArtworkGrid" -import Artists from "./Artists" - -const PageSize = 10 - -interface Props extends RelayProps, React.HTMLProps { - relay?: RelayPaginationProp - filtered_artworks?: any - onChangeUrlQueryParams?: any - for_sale?: boolean - dimension_range?: string - price_range?: string - medium?: string -} - -interface State { - for_sale: boolean - dimension_range: string - price_range: string - medium: string - loading: boolean - showArtists: boolean -} - -const urlPropsQueryConfig = { - for_sale: { type: UrlQueryParamTypes.boolean }, - price_range: { type: UrlQueryParamTypes.string }, - medium: { type: UrlQueryParamTypes.string }, - dimension_range: { type: UrlQueryParamTypes.string }, -} - -export class GeneContents extends React.Component { - constructor(props: Props) { - super(props) - this.state = { - for_sale: props.for_sale || false, - dimension_range: props.dimension_range || "*", - price_range: props.price_range || "*", - medium: props.medium || "*", - loading: false, - showArtists: true, - } - } - - anyArtworkFilters() { - return ( - this.state.for_sale || - (this.state.dimension_range !== "*" && !!this.state.dimension_range) || - (this.state.price_range !== "*" && !!this.state.price_range) || - (this.state.medium !== "*" && !!this.state.medium) - ) - } - - componentWillMount() { - // const { relay, gene } = this.props - // Allow us to set variables from URL params - if (this.anyArtworkFilters()) { - // TODO: Relay Modern - // relay.setVariables({ - // for_sale: this.props.for_sale, - // dimension_range: this.props.dimension_range, - // price_range: this.props.price_range, - // medium: this.props.medium, - // }) - } else { - // TODO: Relay Modern - // relay.setVariables({ - // showArtists: gene.mode === "artist", - // }) - } - } - - onSelect(count, slice) { - this.setState({ - [slice.toLowerCase()]: count.id, - }) - this.props.onChangeUrlQueryParams({ - [slice.toLowerCase()]: count.id, - }) - // TODO: Relay Modern - // this.props.relay.setVariables({ - // [slice.toLowerCase()]: count.id, - // artworksSize: PageSize, - // showArtists: false, - // }) - } - - onChangeSort(option) { - this.props.onChangeUrlQueryParams({ - sort: option.val, - }) - // TODO: Relay Modern - // this.props.relay.setVariables({ - // sort: option.val, - // artworksSize: PageSize, - // showArtists: false, - // }) - } - - setForSale() { - const isForSale = !this.state.for_sale - const forSaleVar = isForSale ? true : null - - this.setState({ - for_sale: isForSale, - }) - this.props.onChangeUrlQueryParams({ - for_sale: forSaleVar, - }) - // TODO: Relay Modern - // this.props.relay.setVariables({ - // for_sale: forSaleVar, - // artworksSize: PageSize, - // showArtists: false, - // }) - } - - loadMoreArtworks() { - const hasMore = this.props.gene.filtered_artworks.artworks.pageInfo.hasNextPage - if (!this.state.loading && hasMore) { - this.setState({ loading: true }, () => { - this.props.relay.loadMore(PageSize, error => { - this.setState({ loading: false }) - }) - }) - } - } - - setShowArtists() { - this.setState({ - dimension_range: null, - price_range: null, - medium: null, - for_sale: false, - }) - this.props.onChangeUrlQueryParams({ - dimension_range: null, - price_range: null, - medium: null, - for_sale: false, - }) - // TODO: Relay Modern - // this.props.relay.setVariables({ - // showArtists: true, - // for_sale: false, - // dimension_range: "*", - // price_range: "*", - // medium: "*", - // }) - } - - render() { - const { filtered_artworks, mode } = this.props.gene - - const { showArtists } = this.state - const shouldShowArtists = showArtists && !this.anyArtworkFilters() - - const dropdowns = filtered_artworks.aggregations.map(aggregation => { - return ( - this.onSelect(count, slice)} - /> - ) - }) - - const pulldownOptions = [ - { val: "-partner_updated_at", name: "Recently Updated" }, - { val: "-year", name: "Artwork Year (desc.)" }, - { val: "year", name: "Artwork Year (asc.)" }, - ] - - const artistFilter = - mode === "artist" ? ( - - By Artists: - - By Work: - - ) : ( - "" - ) - - const content = shouldShowArtists ? ( - - ) : ( -
- -
- - -
- this.onChangeSort(option)} - /> -
- this.loadMoreArtworks()} - /> - {this.state.loading ? : ""} -
- ) - - return ( -
- - {artistFilter} - this.setForSale()} /> - {dropdowns} - - {content} -
- ) - } -} - -const FilterBar = styled.div` - vertical-align: middle; - text-align: center; - - > div { - display: inline-block; - } -` - -const ArtistFilterButtons = styled.div` - margin-right: 10px; - button { - height: 52px; - padding: 16px; - } -` - -const SubFilterBar = styled.div` - display: flex; - justify-content: space-between; - padding: 40px 0 20px; - align-items: center; -` - -const SpinnerContainer = styled.div` - width: 100%; - height: 100px; - position: relative; -` - -const GeneContentsUrl = addUrlProps({ urlPropsQueryConfig })(GeneContents) as React.StatelessComponent - -interface RelayProps { - gene: { - mode: string | null - name: string | null - filtered_artworks: { - aggregations: Array<{ slice: string }> - artworks: { - pageInfo: { - hasNextPage: boolean - endCursor: string - } - } - } - } -} - -export default createPaginationContainer( - GeneContentsUrl, - { - gene: graphql.experimental` - fragment Contents_gene on Gene - @argumentDefinitions( - count: { type: "Int", defaultValue: 10 } - cursor: { type: "String", defaultValue: "" } - showArtists: { type: "Boolean", defaultValue: true } - sort: { type: "String", defaultValue: "-partner_updated_at" } - for_sale: { type: "Boolean", defaultValue: false } - medium: { type: "String", defaultValue: "*" } - aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] } - price_range: { type: "String", defaultValue: "*" } - dimension_range: { type: "String", defaultValue: "*" } - ) { - mode - name - ... on Gene @include(if: $showArtists) { - ...Artists_gene - } - old_filtered_artworks: filtered_artworks( - aggregations: $aggregations - size: $count - for_sale: $for_sale - medium: $medium - price_range: $price_range - dimension_range: $dimension_range - sort: $sort - ) { - ...TotalCount_filter_artworks - aggregations { - slice - ...Dropdown_aggregation - } - artworks: artworks_connection(first: $count, after: $cursor) @connection(key: "Contents_artworks") { - pageInfo { - hasNextPage - endCursor - } - edges { - ...ArtworkGrid_artworks - node { - __id - } - } - - } - } - } - `, - }, - { - direction: "forward", - getConnectionFromProps(props) { - return props.gene.filtered_artworks.artworks as ConnectionData - }, - getFragmentVariables(prevVars, totalCount) { - return { - ...prevVars, - count: totalCount, - } - }, - getVariables(props, { count, cursor }, fragmentVariables) { - return { - // in most cases, for variables other than connection filters like - // `first`, `after`, etc. you may want to use the previous values. - ...fragmentVariables, - count, - cursor, - } - }, - query: graphql.experimental` - query ContentsQuery( - $geneNodeID: ID! - $count: Int! - $cursor: String - $showArtists: Boolean - $sort: String - $for_sale: Boolean - $medium: String - $aggregations: [ArtworkAggregation] - $price_range: String - $dimension_range: String - ) { - node(__id: $geneNodeID) { - ...Contents_gene - @arguments( - count: $count - cursor: $cursor - showArtists: $showArtists - sort: $sort - for_sale: $for_sale - medium: $medium - aggregations: $aggregations - price_range: $price_range - dimension_range: $dimension_range - ) - } - } - `, - } -) diff --git a/src/Components/Gene/NewContents.tsx b/src/Components/Gene/NewContents.tsx deleted file mode 100644 index 8f95fa7e03..0000000000 --- a/src/Components/Gene/NewContents.tsx +++ /dev/null @@ -1,157 +0,0 @@ -import React from "react" -import { graphql, QueryRenderer } from "react-relay" - -import { ContextConsumer, ContextProps } from "../Artsy" -import Artists from "./Artists" -import Artworks from "./Artworks" - -interface Filters { - for_sale: boolean - dimension_range: string - price_range: string - medium: string -} - -interface Props extends ContextProps { - mode: "artists" | "artworks" - filters?: Filters - geneID: string - sort?: string -} - -interface State extends Filters { - mode: "artists" | "artworks" - sort?: string -} - -class GeneNewContents extends React.Component { - constructor(props: Props) { - super(props) - this.state = { - for_sale: null, - medium: "*", - price_range: "*", - dimension_range: "*", - mode: props.mode, - sort: "-partner_updated_at", - } - } - - onDropdownSelect(slice: string, value: string) { - this.setState({ - [slice.toLowerCase() as any]: value, - mode: "artworks", - }) - } - - onForSaleToggleSelect() { - if (this.state.for_sale) { - this.setState({ - for_sale: null, - }) - } else { - this.setState({ - for_sale: true, - }) - } - } - - onSortSelect(sortEl) { - this.setState({ - sort: sortEl.val, - mode: "artworks", - }) - } - - onArtistModeSelect() { - this.setState({ - mode: "artists", - }) - } - - renderArtists() { - const { geneID, relayEnvironment } = this.props - return ( - { - if (props) { - return - } else { - return null - } - }} - /> - ) - } - - renderArtworks() { - const { geneID, relayEnvironment } = this.props - const { for_sale, medium, price_range, dimension_range, sort } = this.state - return ( - { - if (props) { - return ( - - ) - } else { - return null - } - }} - /> - ) - } - - render() { - const { filters } = this.props - const { mode } = this.state - if (mode === "artists" && !filters) { - return this.renderArtists() - } - return this.renderArtworks() - } -} - -export const NewContents = ContextConsumer(GeneNewContents) diff --git a/src/Components/Gene/index.tsx b/src/Components/Gene/index.tsx index 6e0636fb12..e52c0a7627 100644 --- a/src/Components/Gene/index.tsx +++ b/src/Components/Gene/index.tsx @@ -1,36 +1,157 @@ import React from "react" -import { createFragmentContainer, graphql } from "react-relay" -import history from "../History" +import { graphql, QueryRenderer } from "react-relay" -import { configureUrlQuery } from "react-url-query" -import Contents from "./Contents" +import { ContextConsumer, ContextProps } from "../Artsy" +import Artists from "./Artists" +import Artworks from "./Artworks" -interface Props extends RelayProps, React.HTMLProps { - gene: any +interface Filters { + for_sale: boolean + dimension_range: string + price_range: string + medium: string } -export class GenePage extends React.Component { - componentWillMount() { - configureUrlQuery({ history }) +interface Props extends ContextProps { + mode: "artists" | "artworks" + filters?: Filters + geneID: string + sort?: string +} + +interface State extends Filters { + mode: "artists" | "artworks" + sort?: string +} + +class GeneContents extends React.Component { + constructor(props: Props) { + super(props) + this.state = { + for_sale: null, + medium: "*", + price_range: "*", + dimension_range: "*", + mode: props.mode, + sort: "-partner_updated_at", + } } - render() { - const { gene } = this.props - return + onDropdownSelect(slice: string, value: string) { + this.setState({ + [slice.toLowerCase() as any]: value, + mode: "artworks", + }) } -} -export default createFragmentContainer( - GenePage, - graphql` - fragment Gene_gene on Gene { - ...Contents_gene + onForSaleToggleSelect() { + if (this.state.for_sale) { + this.setState({ + for_sale: null, + }) + } else { + this.setState({ + for_sale: true, + }) } - ` -) + } + + onSortSelect(sortEl) { + this.setState({ + sort: sortEl.val, + mode: "artworks", + }) + } -interface RelayProps { - gene: { - mode: string | null + onArtistModeSelect() { + this.setState({ + mode: "artists", + }) + } + + renderArtists() { + const { geneID, relayEnvironment } = this.props + return ( + { + if (props) { + return + } else { + return null + } + }} + /> + ) + } + + renderArtworks() { + const { geneID, relayEnvironment } = this.props + const { for_sale, medium, price_range, dimension_range, sort } = this.state + return ( + { + if (props) { + return ( + + ) + } else { + return null + } + }} + /> + ) + } + + render() { + const { filters } = this.props + const { mode } = this.state + if (mode === "artists" && !filters) { + return this.renderArtists() + } + return this.renderArtworks() } } + +export const Contents = ContextConsumer(GeneContents) diff --git a/src/Components/__stories__/ArtworkGrid.story.tsx b/src/Components/__stories__/ArtworkGrid.story.tsx index bd5789babc..00442f86ad 100644 --- a/src/Components/__stories__/ArtworkGrid.story.tsx +++ b/src/Components/__stories__/ArtworkGrid.story.tsx @@ -13,9 +13,7 @@ function GridExample(props: { artistID: string; currentUser: User }) { query ArtworkGridQuery($artistID: String!) { artist(id: $artistID) { artworks: artworks_connection(first: 10) { - edges { - ...ArtworkGrid_artworks - } + ...ArtworkGrid_artworks } } } diff --git a/src/Components/__stories__/Gene.story.tsx b/src/Components/__stories__/Gene.story.tsx index d52f038442..0d99c85208 100644 --- a/src/Components/__stories__/Gene.story.tsx +++ b/src/Components/__stories__/Gene.story.tsx @@ -1,98 +1,25 @@ import { storiesOf } from "@storybook/react" import React from "react" -import { graphql } from "react-relay" - -import { RootQueryRenderer } from "../../Relay/RootQueryRenderer" -import Gene from "../Gene" -import ArtistRow from "../Gene/ArtistRow" -import { NewContents } from "../Gene/NewContents" +import { Contents } from "../Gene" import { ContextProvider } from "../Artsy" -function GeneExample(props: { geneID: string }) { - return ( - readyState.props && } - /> - ) -} - -function ArtistExample(props: { artistID: string }) { - return ( - readyState.props && } - /> - ) -} - -storiesOf("Components/Rows/Gene", module) - .add("Gene Row - Artist: Stephen Willats", () => { - return ( -
- -
- ) - }) - .add("Gene Row - Artist: Banksy", () => { +storiesOf("Components/Pages/Gene/Contents", module) + .add("Artists Mode - Minimalism", () => { return (
- -
- ) - }) - .add("Gene Row - Artist: Glenn Brown", () => { - return ( -
- -
- ) - }) - -storiesOf("Components/Pages/Gene", module) - .add("Integration - Minimalism", () => { - return ( -
- -
- ) - }) - .add("Integration - The Fantastic", () => { - return ( -
- -
- ) - }) - .add("Integration - Old Master Influenced Fantasy", () => { - return ( -
- + < ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> + +
) }) - storiesOf("Components/Pages/Gene/NewContents", module) - .add("Integration - Minimalism", () => { + .add("Artworks Mode - Animals", () => { return (
< ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> - +
) From dabd6ea1a31d4becf5cd231c3388f979b8b658e4 Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Thu, 14 Dec 2017 14:20:56 -0500 Subject: [PATCH 09/12] Remove root level filter component --- src/Components/ArtworkFilter/index.tsx | 273 ------------------ .../__stories__/ArtworkFilter.story.tsx | 132 --------- 2 files changed, 405 deletions(-) delete mode 100644 src/Components/ArtworkFilter/index.tsx delete mode 100644 src/Components/__stories__/ArtworkFilter.story.tsx diff --git a/src/Components/ArtworkFilter/index.tsx b/src/Components/ArtworkFilter/index.tsx deleted file mode 100644 index 40fc89bea9..0000000000 --- a/src/Components/ArtworkFilter/index.tsx +++ /dev/null @@ -1,273 +0,0 @@ -import React from "react" -import { ConnectionData, createPaginationContainer, graphql, RelayPaginationProp } from "react-relay" -import styled from "styled-components" - -import ArtworkGrid from "../ArtworkGrid" -import BorderedPulldown from "../BorderedPulldown" -import Spinner from "../Spinner" - -import Dropdown from "./Dropdown" -import ForSaleCheckbox from "./ForSaleCheckbox" -import Headline from "./Headline" -import TotalCount from "./TotalCount" - -const PageSize = 10 - -interface Props extends RelayProps, React.HTMLProps { - relay: RelayPaginationProp - for_sale?: boolean - dimension_range?: string - price_range?: string - medium?: string -} - -interface State { - for_sale: boolean - dimension_range: string - price_range: string - medium: string - loading: boolean -} - -class ArtworkFilter extends React.Component { - constructor(props: Props) { - super(props) - this.state = { - for_sale: props.for_sale || false, - dimension_range: props.dimension_range || "*", - price_range: props.price_range || "*", - medium: props.medium || "*", - loading: false, - } - } - - handleLoadMore() { - if (!this.state.loading && this.props.viewer.filter_artworks.artworks.pageInfo.hasNextPage) { - this.setState({ loading: true }, () => { - this.props.relay.loadMore(PageSize, error => { - this.setState({ loading: false }) - }) - }) - } - } - - setForSale() { - const isForSale = !this.state.for_sale - // const forSaleVar = isForSale ? true : null - - this.setState({ - for_sale: isForSale, - }) - // TODO: Relay Modern - // this.props.relay.setVariables({ - // for_sale: forSaleVar, - // size: PageSize, - // }) - } - - onSelect(count, slice) { - this.setState({ - [slice.toLowerCase()]: count.id, - }) - // TODO: Relay Modern - // this.props.relay.setVariables({ - // [slice.toLowerCase()]: count.id, - // size: PageSize, - // }) - } - - onChangeSort(option) { - // TODO: Relay Modern - // this.props.relay.setVariables({ - // sort: option.val, - // size: PageSize, - // }) - } - - render() { - const filterArtworks = this.props.viewer.filter_artworks - const dropdowns = filterArtworks.aggregations.map(aggregation => ( - this.onSelect(count, slice)} - /> - )) - const pulldownOptions = [ - { val: "-partner_updated_at", name: "Recently Updated" }, - { val: "-year", name: "Artwork Year (desc.)" }, - { val: "year", name: "Artwork Year (asc.)" }, - ] - - return ( -
- - this.setForSale()} /> - {dropdowns} - - -
- - -
- this.onChangeSort(option)} - /> -
- this.handleLoadMore()} - columnCount={4} - /> - {this.state.loading ? : ""} -
- ) - } -} - -const FilterBar = styled.div` - text-align: center; -` - -const SubFilterBar = styled.div` - display: flex; - justify-content: space-between; - padding: 40px 0 20px; - align-items: center; -` - -const SpinnerContainer = styled.div` - width: 100%; - height: 200px; - position: relative; -` - -export default createPaginationContainer( - ArtworkFilter, - { - viewer: graphql.experimental` - fragment ArtworkFilter_viewer on Viewer - @argumentDefinitions( - count: { type: "Int", defaultValue: 10 } - cursor: { type: "String", defaultValue: "" } - sort: { type: "String", defaultValue: "-partner_updated_at" } - for_sale: { type: "Boolean", defaultValue: false } - medium: { type: "String", defaultValue: "*" } - aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] } - price_range: { type: "String", defaultValue: "*" } - dimension_range: { type: "String", defaultValue: "*" } - ) { - filter_artworks( - aggregations: $aggregations - size: $count - for_sale: $for_sale - medium: $medium - price_range: $price_range - dimension_range: $dimension_range - sort: $sort - ) { - aggregations { - slice - counts { - id - name - } - ...Dropdown_aggregation - } - ...TotalCount_filter_artworks - artworks: artworks_connection(first: $count, after: $cursor) - @connection(key: "ArtworkFilter_filter_artworks") { - pageInfo { - hasNextPage - endCursor - } - edges { - - node { - __id - } - } - ...ArtworkGrid_artworks - } - facet { - ...Headline_facet - } - } - } - `, - }, - { - direction: "forward", - getConnectionFromProps(props) { - return props.viewer.filter_artworks.artworks as ConnectionData - }, - getFragmentVariables(prevVars, totalCount) { - return { - ...prevVars, - count: totalCount, - } - }, - getVariables(props, { count, cursor }, fragmentVariables) { - return { - // in most cases, for variables other than connection filters like - // `first`, `after`, etc. you may want to use the previous values. - ...fragmentVariables, - count, - cursor, - } - }, - query: graphql.experimental` - query ArtworkFilterQuery( - $count: Int! - $cursor: String - $sort: String - $for_sale: Boolean - $medium: String - $aggregations: [ArtworkAggregation] - $price_range: String - $dimension_range: String - ) { - viewer { - ...ArtworkFilter_filter_artworks - @arguments( - count: $count - cursor: $cursor - sort: $sort - for_sale: $for_sale - medium: $medium - aggregations: $aggregations - price_range: $price_range - dimension_range: $dimension_range - ) - } - } - `, - } -) - -interface RelayProps { - viewer: { - filter_artworks: { - artworks: { - pageInfo: { - hasNextPage: boolean - endCursor: string - } - } | null - counts: { - total: number | null - } | null - aggregations: Array | null - facet: any - } | null - } | null -} diff --git a/src/Components/__stories__/ArtworkFilter.story.tsx b/src/Components/__stories__/ArtworkFilter.story.tsx deleted file mode 100644 index 6b16b01b76..0000000000 --- a/src/Components/__stories__/ArtworkFilter.story.tsx +++ /dev/null @@ -1,132 +0,0 @@ -import { storiesOf } from "@storybook/react" -import React from "react" -import { createFragmentContainer, graphql } from "react-relay" - -import { RootQueryRenderer } from "../../Relay/RootQueryRenderer" -import ArtworkFilter from "../ArtworkFilter" -import Dropdown from "../ArtworkFilter/Dropdown" -import TotalCount from "../ArtworkFilter/TotalCount" - -interface FilterArtworksDropdownState { - selected: string -} - -class FilterArtworksDropdown extends React.Component { - constructor(props) { - super(props) - this.state = { - selected: "", - } - } - - showSelection(count) { - this.setState({ - selected: count.name, - }) - } - - render() { - const dropdowns = this.props.filter_artworks.filter_artworks.aggregations.map(aggregation => ( - - )) - - const selected =
{this.state.selected}
- - return ( -
-
{dropdowns}
-
Selected: {selected}
-
- ) - } -} - -const FilterArtworksDropdownContainer = createFragmentContainer( - FilterArtworksDropdown, - graphql` - fragment ArtworkFilter_filter_artworks on Viewer { - filter_artworks(aggregations: [MEDIUM, GALLERY], artist_id: "christopher-williams") { - aggregations { - slice - ...Dropdown_aggregation - } - } - } - ` -) - -interface DropdownRelayProps { - filter_artworks: { - filter_artworks: { - aggregations: Array<{ - slice: string | null - } | null> | null - } | null - } | null -} - -function FilterArtworksDropdownExample() { - return ( - { - return readyState.props && - }} - /> - ) -} - -function FilterArtworksTotalCountExample() { - return ( - { - return readyState.props && - }} - /> - ) -} - -function FilterArtworksExample() { - const user = { - id: "some-id", - accessToken: "some-token", - } as User - return ( - { - return readyState.props && - }} - /> - ) -} - -storiesOf("Components/Artwork/Artwork Filter Components", module) - .add("All Artworks - Artwork filter", () => ) - .add("Filter dropdown", () => ) - .add("Total Count", () => ) From 300bf1c285ca2bd64815012813d23bbd236da8cb Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Thu, 14 Dec 2017 16:27:51 -0500 Subject: [PATCH 10/12] Add tag page --- data/schema.graphql | 102 +- data/schema.json | 954 +++++++++++++++++- externals/metaphysics | 2 +- package.json | 2 +- .../Gene/{Artworks.tsx => GeneArtworks.tsx} | 12 +- src/Components/Gene/GeneArtworksContent.tsx | 119 +++ src/Components/Gene/index.tsx | 10 +- src/Components/Tag/TagArtworks.tsx | 169 ++++ .../TagArtworksContent.tsx} | 12 +- src/Components/Tag/index.tsx | 111 ++ src/Components/__stories__/Tag.story.tsx | 16 + src/Components/index.tsx | 2 - 12 files changed, 1484 insertions(+), 27 deletions(-) rename src/Components/Gene/{Artworks.tsx => GeneArtworks.tsx} (93%) create mode 100644 src/Components/Gene/GeneArtworksContent.tsx create mode 100644 src/Components/Tag/TagArtworks.tsx rename src/Components/{Gene/ArtworksContent.tsx => Tag/TagArtworksContent.tsx} (88%) create mode 100644 src/Components/Tag/index.tsx create mode 100644 src/Components/__stories__/Tag.story.tsx diff --git a/data/schema.graphql b/data/schema.graphql index 32305e5a2a..44de941e90 100644 --- a/data/schema.graphql +++ b/data/schema.graphql @@ -1028,7 +1028,7 @@ type ArtworkEdge { union ArtworkFilterFacet = ArtworkFilterTag | ArtworkFilterGene -type ArtworkFilterGene { +type ArtworkFilterGene implements Node { # A globally unique ID. __id: ID! @@ -1043,9 +1043,41 @@ type ArtworkFilterGene { href: String image: Image count: Int + + # Artworks Elastic Search results + filtered_artworks( + aggregation_partner_cities: [String] + aggregations: [ArtworkAggregation] + artist_id: String + artist_ids: [String] + color: String + dimension_range: String + extra_aggregation_gene_ids: [String] + include_artworks_by_followed_artists: Boolean + for_sale: Boolean + gene_id: String + gene_ids: [String] + height: String + width: String + + # A string from the list of allocations, or * to denote all mediums + medium: String + period: String + periods: [String] + major_periods: [String] + partner_id: ID + partner_cities: [String] + price_range: String + page: Int + sale_id: ID + size: Int + sort: String + tag_id: String + keyword: String + ): FilterArtworks } -type ArtworkFilterTag { +type ArtworkFilterTag implements Node { # A globally unique ID. __id: ID! @@ -1060,6 +1092,38 @@ type ArtworkFilterTag { href: String image: Image count: Int + + # Artworks Elastic Search results + filtered_artworks( + aggregation_partner_cities: [String] + aggregations: [ArtworkAggregation] + artist_id: String + artist_ids: [String] + color: String + dimension_range: String + extra_aggregation_gene_ids: [String] + include_artworks_by_followed_artists: Boolean + for_sale: Boolean + gene_id: String + gene_ids: [String] + height: String + width: String + + # A string from the list of allocations, or * to denote all mediums + medium: String + period: String + periods: [String] + major_periods: [String] + partner_id: ID + partner_cities: [String] + price_range: String + page: Int + sale_id: ID + size: Int + sort: String + tag_id: String + keyword: String + ): FilterArtworks } type ArtworkInquiry { @@ -5243,7 +5307,7 @@ enum SubmissionStateAggregation { REJECTED } -type Tag { +type Tag implements Node { # A globally unique ID. __id: ID! @@ -5258,6 +5322,38 @@ type Tag { href: String image: Image count: Int + + # Artworks Elastic Search results + filtered_artworks( + aggregation_partner_cities: [String] + aggregations: [ArtworkAggregation] + artist_id: String + artist_ids: [String] + color: String + dimension_range: String + extra_aggregation_gene_ids: [String] + include_artworks_by_followed_artists: Boolean + for_sale: Boolean + gene_id: String + gene_ids: [String] + height: String + width: String + + # A string from the list of allocations, or * to denote all mediums + medium: String + period: String + periods: [String] + major_periods: [String] + partner_id: ID + partner_cities: [String] + price_range: String + page: Int + sale_id: ID + size: Int + sort: String + tag_id: String + keyword: String + ): FilterArtworks } type TrendingArtists { diff --git a/data/schema.json b/data/schema.json index 9b7b8dc405..6e47c2c78d 100644 --- a/data/schema.json +++ b/data/schema.json @@ -2709,6 +2709,16 @@ "name": "FilterArtworks", "ofType": null }, + { + "kind": "OBJECT", + "name": "ArtworkFilterTag", + "ofType": null + }, + { + "kind": "OBJECT", + "name": "ArtworkFilterGene", + "ofType": null + }, { "kind": "OBJECT", "name": "Gene", @@ -2798,6 +2808,11 @@ "kind": "OBJECT", "name": "PartnerShowSearchEntity", "ofType": null + }, + { + "kind": "OBJECT", + "name": "Tag", + "ofType": null } ] }, @@ -19876,10 +19891,321 @@ }, "isDeprecated": false, "deprecationReason": null + }, + { + "name": "filtered_artworks", + "description": "Artworks Elastic Search results", + "args": [ + { + "name": "aggregation_partner_cities", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "aggregations", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "ENUM", + "name": "ArtworkAggregation", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "artist_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "artist_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "color", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "dimension_range", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "extra_aggregation_gene_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "include_artworks_by_followed_artists", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "for_sale", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "gene_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "gene_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "height", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "width", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "medium", + "description": "A string from the list of allocations, or * to denote all mediums", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "period", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "periods", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "major_periods", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "partner_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "partner_cities", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "price_range", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "page", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "sale_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "size", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "sort", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "tag_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "keyword", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "FilterArtworks", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null } ], "inputFields": null, - "interfaces": [], + "interfaces": [ + { + "kind": "INTERFACE", + "name": "Node", + "ofType": null + } + ], "enumValues": null, "possibleTypes": null }, @@ -20007,10 +20333,321 @@ }, "isDeprecated": false, "deprecationReason": null + }, + { + "name": "filtered_artworks", + "description": "Artworks Elastic Search results", + "args": [ + { + "name": "aggregation_partner_cities", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "aggregations", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "ENUM", + "name": "ArtworkAggregation", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "artist_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "artist_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "color", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "dimension_range", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "extra_aggregation_gene_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "include_artworks_by_followed_artists", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "for_sale", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "gene_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "gene_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "height", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "width", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "medium", + "description": "A string from the list of allocations, or * to denote all mediums", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "period", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "periods", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "major_periods", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "partner_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "partner_cities", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "price_range", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "page", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "sale_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "size", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "sort", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "tag_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "keyword", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "FilterArtworks", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null } ], "inputFields": null, - "interfaces": [], + "interfaces": [ + { + "kind": "INTERFACE", + "name": "Node", + "ofType": null + } + ], "enumValues": null, "possibleTypes": null }, @@ -38121,10 +38758,321 @@ }, "isDeprecated": false, "deprecationReason": null + }, + { + "name": "filtered_artworks", + "description": "Artworks Elastic Search results", + "args": [ + { + "name": "aggregation_partner_cities", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "aggregations", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "ENUM", + "name": "ArtworkAggregation", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "artist_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "artist_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "color", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "dimension_range", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "extra_aggregation_gene_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "include_artworks_by_followed_artists", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "for_sale", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "gene_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "gene_ids", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "height", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "width", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "medium", + "description": "A string from the list of allocations, or * to denote all mediums", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "period", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "periods", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "major_periods", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "partner_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "partner_cities", + "description": null, + "type": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null + }, + { + "name": "price_range", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "page", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "sale_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "size", + "description": null, + "type": { + "kind": "SCALAR", + "name": "Int", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "sort", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "tag_id", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "keyword", + "description": null, + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "FilterArtworks", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null } ], "inputFields": null, - "interfaces": [], + "interfaces": [ + { + "kind": "INTERFACE", + "name": "Node", + "ofType": null + } + ], "enumValues": null, "possibleTypes": null }, diff --git a/externals/metaphysics b/externals/metaphysics index 40ef926133..d0b7d162e1 160000 --- a/externals/metaphysics +++ b/externals/metaphysics @@ -1 +1 @@ -Subproject commit 40ef9261337abcc931ad36bdc5843d9ca51ec7fa +Subproject commit d0b7d162e18078dff55f3f9ddd37097302a51e33 diff --git a/package.json b/package.json index b64a824f72..2fca235606 100644 --- a/package.json +++ b/package.json @@ -22,7 +22,7 @@ "test:watch": "jest --watch --runInBand", "storybook": "node verify-node-version.js && concurrently --kill-others 'yarn relay --watch' 'env GRAPHQL_NO_NAME_WARNING=true start-storybook -p 9001'", "deploy-storybook": "yarn relay && NODE_ENV=production storybook-to-ghpages", - "sync-schema": "cd externals/metaphysics && git fetch && git checkout origin/master && yarn install && npm run dump-schema -- ../../data", + "sync-schema": "cd externals/metaphysics && git fetch && git checkout origin/tag_filter && yarn install && npm run dump-schema -- ../../data", "sync-schema:localhost": "cd ../metaphysics && yarn dump-schema -- ../emission/data", "sync-colors": "cd externals/elan && git fetch && git checkout origin/master && cp components/lib/variables/colors.json ../../data", "lint": "tslint -c tslint.json --project tsconfig.json", diff --git a/src/Components/Gene/Artworks.tsx b/src/Components/Gene/GeneArtworks.tsx similarity index 93% rename from src/Components/Gene/Artworks.tsx rename to src/Components/Gene/GeneArtworks.tsx index 33a966c27e..1f71002451 100644 --- a/src/Components/Gene/Artworks.tsx +++ b/src/Components/Gene/GeneArtworks.tsx @@ -13,7 +13,7 @@ import TotalCount from "../ArtworkFilter/TotalCount" import BorderedPulldown from "../BorderedPulldown" -import ArtworksContent from "./ArtworksContent" +import GeneArtworksContent from "./GeneArtworksContent" interface Filters { for_sale?: boolean @@ -59,7 +59,7 @@ const ArtistFilterButtons = styled.div` } ` -export class Artworks extends React.Component { +export class GeneArtworks extends React.Component { constructor(props: Props) { super(props) this.state = { @@ -124,7 +124,7 @@ export class Artworks extends React.Component {
- + ) } @@ -144,10 +144,10 @@ export class Artworks extends React.Component { } export default createFragmentContainer( - Artworks, + GeneArtworks, { gene: graphql.experimental` - fragment Artworks_gene on Gene + fragment GeneArtworks_gene on Gene @argumentDefinitions( for_sale: { type: "Boolean" } medium: { type: "String", defaultValue: "*" } @@ -164,7 +164,7 @@ export default createFragmentContainer( size: 0 ) { ...TotalCount_filter_artworks - ...ArtworksContent_filtered_artworks + ...GeneArtworksContent_filtered_artworks aggregations { slice counts { diff --git a/src/Components/Gene/GeneArtworksContent.tsx b/src/Components/Gene/GeneArtworksContent.tsx new file mode 100644 index 0000000000..159c43bfc5 --- /dev/null +++ b/src/Components/Gene/GeneArtworksContent.tsx @@ -0,0 +1,119 @@ +import * as React from "react" +import {ConnectionData, createPaginationContainer,graphql, RelayPaginationProp} from "react-relay" +import styled from "styled-components" +import ArtworkGrid from "../ArtworkGrid" +import Spinner from "../Spinner" + +interface Props extends RelayProps { + relay?: RelayPaginationProp +} + +const SpinnerContainer = styled.div` + width: 100%; + height: 100px; + position: relative; +` + +const PageSize = 10 + +export class GeneArtworksContent extends React.Component { + loadMoreArtworks() { + const hasMore = this.props.filtered_artworks.artworks.pageInfo.hasNextPage + if (hasMore && !this.props.relay.isLoading()) { + this.props.relay.loadMore(PageSize, error => { + if (error) { + console.error(error) + } + }) + } + } + + render() { + return ( +
+ this.loadMoreArtworks()} + /> + {this.props.relay.isLoading() ? : ""} +
+ ) + } +} + +export default createPaginationContainer( + GeneArtworksContent, + { + filtered_artworks: graphql.experimental` + fragment GeneArtworksContent_filtered_artworks on FilterArtworks + @argumentDefinitions( + count: { type: "Int", defaultValue: 10 } + cursor: { type: "String", defaultValue: "" } + ) { + __id + artworks: artworks_connection(first: $count, after: $cursor, sort: $sort) @connection(key: "GeneArtworksContent_filtered_artworks") { + pageInfo { + hasNextPage + endCursor + } + ...ArtworkGrid_artworks + edges { + node { + __id + } + } + } + } + `, + }, + { + direction: "forward", + getConnectionFromProps(props) { + return props.filtered_artworks.artworks as ConnectionData + }, + getFragmentVariables(prevVars, totalCount) { + return { + ...prevVars, + count: totalCount, + } + }, + getVariables(props, { count, cursor }, fragmentVariables) { + return { + // in most cases, for variables other than connection filters like + // `first`, `after`, etc. you may want to use the previous values. + ...fragmentVariables, + count, + cursor, + filteredArtworksNodeID: props.filtered_artworks.__id, + } + }, + query: graphql.experimental` + query GeneArtworksContentQuery( + $filteredArtworksNodeID: ID! + $count: Int! + $cursor: String + $sort: String + ) { + node(__id: $filteredArtworksNodeID) { + ...GeneArtworksContent_filtered_artworks @arguments( + count: $count, + cursor: $cursor, + ) + } + } + `, + } +) + +interface RelayProps { + filtered_artworks: { + artworks: { + edges: Array<{}> + pageInfo: { + hasNextPage: boolean + } + } + } +} diff --git a/src/Components/Gene/index.tsx b/src/Components/Gene/index.tsx index e52c0a7627..cf047c6477 100644 --- a/src/Components/Gene/index.tsx +++ b/src/Components/Gene/index.tsx @@ -3,7 +3,7 @@ import { graphql, QueryRenderer } from "react-relay" import { ContextConsumer, ContextProps } from "../Artsy" import Artists from "./Artists" -import Artworks from "./Artworks" +import GeneArtworks from "./GeneArtworks" interface Filters { for_sale: boolean @@ -75,7 +75,7 @@ class GeneContents extends React.Component { { { $dimension_range: String ) { gene(id: $geneID) { - ...Artworks_gene + ...GeneArtworks_gene @arguments( for_sale: $for_sale medium: $medium @@ -123,7 +123,7 @@ class GeneContents extends React.Component { render={({ props }) => { if (props) { return ( - void + onSortSelected: (sort: string) => void + onForSaleToggleSelected: () => void + sort?: string +} + +interface State extends Filters { + loading: boolean +} + +const FilterBar = styled.div` + vertical-align: middle; + text-align: center; + + > div { + display: inline-block; + } +` + +const SubFilterBar = styled.div` + display: flex; + justify-content: space-between; + padding: 40px 0 20px; + align-items: center; +` + +export class TagArtworks extends React.Component { + constructor(props: Props) { + super(props) + this.state = { + loading: false, + } + } + + renderDropdown() { + return this.props.tag.filtered_artworks.aggregations.map(aggregation => { + return ( + + ) + }) + } + + renderForSaleToggle() { + return + } + + renderArtworks() { + const pulldownOptions = [ + { val: "-partner_updated_at", name: "Recently Updated" }, + { val: "-year", name: "Artwork Year (desc.)" }, + { val: "year", name: "Artwork Year (asc.)" }, + ] + const selectedSort = pulldownOptions.find((sort) => sort.val === this.props.sort) + return ( +
+ +
+ + +
+ +
+ +
+ ) + } + + render() { + return ( +
+ + {this.renderForSaleToggle()} + {this.renderDropdown()} + + {this.renderArtworks()} +
+ ) + } +} + +export default createFragmentContainer( + TagArtworks, + { + tag: graphql.experimental` + fragment TagArtworks_tag on Tag + @argumentDefinitions( + for_sale: { type: "Boolean" } + medium: { type: "String", defaultValue: "*" } + aggregations: { type: "[ArtworkAggregation]", defaultValue: [MEDIUM, TOTAL, PRICE_RANGE, DIMENSION_RANGE] } + price_range: { type: "String", defaultValue: "*" } + dimension_range: { type: "String", defaultValue: "*" } + ) { + filtered_artworks( + aggregations: $aggregations + for_sale: $for_sale + medium: $medium + price_range: $price_range + dimension_range: $dimension_range + size: 0 + ) { + ...TotalCount_filter_artworks + ...TagArtworksContent_filtered_artworks + aggregations { + slice + counts { + name + id + } + ...Dropdown_aggregation + } + facet { + ...Headline_facet + } + } + } + `, + }, +) + +interface RelayProps { + tag: { + __id: string + filtered_artworks: { + aggregations: Array<{ + slice: string + counts: { + name: string | null + id: string | null + } + }> + facet: any + } + } +} diff --git a/src/Components/Gene/ArtworksContent.tsx b/src/Components/Tag/TagArtworksContent.tsx similarity index 88% rename from src/Components/Gene/ArtworksContent.tsx rename to src/Components/Tag/TagArtworksContent.tsx index 935e9b7a41..be0c42ad69 100644 --- a/src/Components/Gene/ArtworksContent.tsx +++ b/src/Components/Tag/TagArtworksContent.tsx @@ -16,7 +16,7 @@ const SpinnerContainer = styled.div` const PageSize = 10 -export class ArtworksContent extends React.Component { +export class TagArtworksContent extends React.Component { loadMoreArtworks() { const hasMore = this.props.filtered_artworks.artworks.pageInfo.hasNextPage if (hasMore && !this.props.relay.isLoading()) { @@ -44,16 +44,16 @@ export class ArtworksContent extends React.Component { } export default createPaginationContainer( - ArtworksContent, + TagArtworksContent, { filtered_artworks: graphql.experimental` - fragment ArtworksContent_filtered_artworks on FilterArtworks + fragment TagArtworksContent_filtered_artworks on FilterArtworks @argumentDefinitions( count: { type: "Int", defaultValue: 10 } cursor: { type: "String", defaultValue: "" } ) { __id - artworks: artworks_connection(first: $count, after: $cursor, sort: $sort) @connection(key: "ArtworksContent_filtered_artworks") { + artworks: artworks_connection(first: $count, after: $cursor, sort: $sort) @connection(key: "TagArtworksContent_filtered_artworks") { pageInfo { hasNextPage endCursor @@ -90,14 +90,14 @@ export default createPaginationContainer( } }, query: graphql.experimental` - query ArtworksContentQuery( + query TagArtworksContentQuery( $filteredArtworksNodeID: ID! $count: Int! $cursor: String $sort: String ) { node(__id: $filteredArtworksNodeID) { - ...ArtworksContent_filtered_artworks @arguments( + ...TagArtworksContent_filtered_artworks @arguments( count: $count, cursor: $cursor, ) diff --git a/src/Components/Tag/index.tsx b/src/Components/Tag/index.tsx new file mode 100644 index 0000000000..d451784c83 --- /dev/null +++ b/src/Components/Tag/index.tsx @@ -0,0 +1,111 @@ +import React from "react" +import { graphql, QueryRenderer } from "react-relay" + +import { ContextConsumer, ContextProps } from "../Artsy" +import TagArtworks from "./TagArtworks" + +interface Filters { + for_sale: boolean + dimension_range: string + price_range: string + medium: string +} + +interface Props extends ContextProps { + filters?: Filters + tagID: string + sort?: string +} + +interface State extends Filters { + sort?: string +} + +class TagContents extends React.Component { + constructor(props: Props) { + super(props) + this.state = { + for_sale: null, + medium: "*", + price_range: "*", + dimension_range: "*", + sort: "-partner_updated_at", + } + } + + onDropdownSelect(slice: string, value: string) { + this.setState({ + [slice.toLowerCase() as any]: value, + }) + } + + onForSaleToggleSelect() { + if (this.state.for_sale) { + this.setState({ + for_sale: null, + }) + } else { + this.setState({ + for_sale: true, + }) + } + } + + onSortSelect(sortEl) { + this.setState({ + sort: sortEl.val, + }) + } + + render() { + const { tagID, relayEnvironment } = this.props + const { for_sale, medium, price_range, dimension_range, sort } = this.state + return ( + { + if (props) { + return ( + + ) + } else { + return null + } + }} + /> + ) + } +} + +export const Contents = ContextConsumer(TagContents) diff --git a/src/Components/__stories__/Tag.story.tsx b/src/Components/__stories__/Tag.story.tsx new file mode 100644 index 0000000000..007fdb5f82 --- /dev/null +++ b/src/Components/__stories__/Tag.story.tsx @@ -0,0 +1,16 @@ +import { storiesOf } from "@storybook/react" +import React from "react" +import { Contents } from "../Tag" + +import { ContextProvider } from "../Artsy" + +storiesOf("Components/Pages/Tag/Contents", module) + .add("Butt", () => { + return ( +
+ < ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> + + +
+ ) + }) diff --git a/src/Components/index.tsx b/src/Components/index.tsx index b9cab5c0c6..6b4bdcbf14 100644 --- a/src/Components/index.tsx +++ b/src/Components/index.tsx @@ -1,5 +1,4 @@ import Artwork from "./Artwork" -import ArtworkFilter from "./ArtworkFilter" import ArtworkGrid from "./ArtworkGrid" import BorderedPulldown from "./BorderedPulldown" import Buttons from "./Buttons" @@ -35,7 +34,6 @@ export function init(options: InitOptions) { export default { Artwork, - ArtworkFilter, Buttons, Modal, ArtworkGrid, From 17930d31a4639440d58f53cb29cd0e68e8c6e563 Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Thu, 14 Dec 2017 17:20:46 -0500 Subject: [PATCH 11/12] Callback for state change on gene and tag filter --- src/Components/Gene/index.tsx | 49 +++++++++++++++-------- src/Components/Tag/index.tsx | 40 ++++++++++++------ src/Components/__stories__/Gene.story.tsx | 4 +- src/Components/__stories__/Tag.story.tsx | 2 +- 4 files changed, 63 insertions(+), 32 deletions(-) diff --git a/src/Components/Gene/index.tsx b/src/Components/Gene/index.tsx index cf047c6477..68a2af9054 100644 --- a/src/Components/Gene/index.tsx +++ b/src/Components/Gene/index.tsx @@ -12,16 +12,27 @@ interface Filters { medium: string } +type Sort = "year" | "-year" | "-partner_updated_at" + +type Mode = "artists" | "artworks" + +interface StateChangePayload { + filters: Filters + sort: Sort + mode: Mode +} + interface Props extends ContextProps { - mode: "artists" | "artworks" + mode: Mode filters?: Filters geneID: string - sort?: string + sort?: Sort + onStateChange: (payload: StateChangePayload) => void } interface State extends Filters { - mode: "artists" | "artworks" - sort?: string + mode: Mode + sort?: Sort } class GeneContents extends React.Component { @@ -37,36 +48,42 @@ class GeneContents extends React.Component { } } + handleStateChange = () => { + const { for_sale, medium, price_range, dimension_range, sort, mode } = this.state + const filters = { + for_sale, + medium, + price_range, + dimension_range, + } + this.props.onStateChange({ filters, sort, mode }) + } + onDropdownSelect(slice: string, value: string) { this.setState({ [slice.toLowerCase() as any]: value, mode: "artworks", - }) + }, this.handleStateChange) } onForSaleToggleSelect() { - if (this.state.for_sale) { - this.setState({ - for_sale: null, - }) - } else { - this.setState({ - for_sale: true, - }) - } + const forSale = this.state.for_sale ? null : true + this.setState({ + for_sale: forSale, + }, this.handleStateChange) } onSortSelect(sortEl) { this.setState({ sort: sortEl.val, mode: "artworks", - }) + }, this.handleStateChange) } onArtistModeSelect() { this.setState({ mode: "artists", - }) + }, this.handleStateChange) } renderArtists() { diff --git a/src/Components/Tag/index.tsx b/src/Components/Tag/index.tsx index d451784c83..6bf63eb919 100644 --- a/src/Components/Tag/index.tsx +++ b/src/Components/Tag/index.tsx @@ -11,14 +11,22 @@ interface Filters { medium: string } +type Sort = "year" | "-year" | "-partner_updated_at" + +interface StateChangePayload { + filters: Filters + sort: Sort +} + interface Props extends ContextProps { filters?: Filters tagID: string - sort?: string + sort?: Sort + onStateChange: (payload: StateChangePayload) => void } interface State extends Filters { - sort?: string + sort?: Sort } class TagContents extends React.Component { @@ -33,28 +41,34 @@ class TagContents extends React.Component { } } + handleStateChange = () => { + const { for_sale, medium, price_range, dimension_range, sort } = this.state + const filters = { + for_sale, + medium, + price_range, + dimension_range, + } + this.props.onStateChange({ filters, sort }) + } + onDropdownSelect(slice: string, value: string) { this.setState({ [slice.toLowerCase() as any]: value, - }) + }, this.handleStateChange) } onForSaleToggleSelect() { - if (this.state.for_sale) { - this.setState({ - for_sale: null, - }) - } else { - this.setState({ - for_sale: true, - }) - } + const forSale = this.state.for_sale ? null : true + this.setState({ + for_sale: forSale, + }, this.handleStateChange) } onSortSelect(sortEl) { this.setState({ sort: sortEl.val, - }) + }, this.handleStateChange) } render() { diff --git a/src/Components/__stories__/Gene.story.tsx b/src/Components/__stories__/Gene.story.tsx index 0d99c85208..2a579cce46 100644 --- a/src/Components/__stories__/Gene.story.tsx +++ b/src/Components/__stories__/Gene.story.tsx @@ -9,7 +9,7 @@ storiesOf("Components/Pages/Gene/Contents", module) return (
< ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> - +
) @@ -19,7 +19,7 @@ storiesOf("Components/Pages/Gene/Contents", module) return (
< ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> - +
) diff --git a/src/Components/__stories__/Tag.story.tsx b/src/Components/__stories__/Tag.story.tsx index 007fdb5f82..6f3f2b72df 100644 --- a/src/Components/__stories__/Tag.story.tsx +++ b/src/Components/__stories__/Tag.story.tsx @@ -9,7 +9,7 @@ storiesOf("Components/Pages/Tag/Contents", module) return (
< ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> - +
) From a89ff30ac1d3c21a8e43843dfcb3dc06c3b482ec Mon Sep 17 00:00:00 2001 From: Matthew Zikherman Date: Thu, 14 Dec 2017 17:36:02 -0500 Subject: [PATCH 12/12] Remove staging credentials --- src/Components/__stories__/Gene.story.tsx | 4 ++-- src/__stories__/config.js | 14 ++++++++------ 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/src/Components/__stories__/Gene.story.tsx b/src/Components/__stories__/Gene.story.tsx index 2a579cce46..564e9e24e9 100644 --- a/src/Components/__stories__/Gene.story.tsx +++ b/src/Components/__stories__/Gene.story.tsx @@ -8,7 +8,7 @@ storiesOf("Components/Pages/Gene/Contents", module) .add("Artists Mode - Minimalism", () => { return (
- < ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> + < ContextProvider currentUser={{id: "", name: "", accessToken: ""}}>
@@ -18,7 +18,7 @@ storiesOf("Components/Pages/Gene/Contents", module) .add("Artworks Mode - Animals", () => { return (
- < ContextProvider currentUser={{id: "58ed621f9c18db55bc6b2dde", name: "Matt", accessToken: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1OGVkNjIxZjljMThkYjU1YmM2YjJkZGUiLCJzYWx0X2hhc2giOiI2ZTVkMWVhYzJmMWQzNDhmZmZmOGJmMDAyOGQ1OTViOCIsInJvbGVzIjoidXNlciIsInBhcnRuZXJfaWRzIjpbXSwiZXhwIjoxNTE3NzYwMjA0LCJpYXQiOjE1MTI1NzYyMDQsImF1ZCI6IjRlMzZlZmE0ZGI0ZTMyMDAwMTAwMDM1OSIsImlzcyI6IkdyYXZpdHkiLCJqdGkiOiI1YTI4MTRjYzhiM2I4MTQ1ZjI2YTliNzUifQ.ksCRUaQRvGNRW2VnOSAAT32r9PM9s04axn7SqI-_Kno"}}> + < ContextProvider currentUser={{id: "", name: "", accessToken: ""}}>
diff --git a/src/__stories__/config.js b/src/__stories__/config.js index 344a98a5c3..db8e1cdbfe 100644 --- a/src/__stories__/config.js +++ b/src/__stories__/config.js @@ -14,9 +14,11 @@ Events.onEvent(data => { console.log("Tracked event", data) }) -setOptions({ - name: "Reaction", - url: "http://artsy.github.io/reaction", - showDownPanel: false, - sortStoriesByKind: true, -}) + +// TODO: Fix the below +// setOptions({ +// name: "Reaction", +// url: "http://artsy.github.io/reaction", +// showDownPanel: false, +// sortStoriesByKind: true, +// })