"""DDEX schema tests.""" from ddex_ingester_common.helpers.xml_document_helper import ( get_root_element ) from ddex_ingester_common.models.ddex.deal import Deal from ddex_ingester_common.models.ddex.instant_gratification import ( InstantGratification) from ddex_ingester_common.models.ddex.marketing_highlight import ( MarketingHighlight ) from ddex_ingester_common.models.ddex.participant import Participant from ddex_ingester_common.models.ddex.product import Product from ddex_ingester_common.models.ddex.project import Project from ddex_ingester_common.models.ddex.store import Store from ddex_ingester_common.models.ddex.track import Track from ddex_ingester_common.models.ddex.video import Video from ddex_ingester_common.schemas.ddex_schema import DDEXSchema from marshmallow import ValidationError import pytest def test_ddex_schema_deserialize(ddex_combined_metadata): """Test deseralizing DDEX document into context dict with objects.""" deserialized_context = DDEXSchema().load(ddex_combined_metadata) assert type(deserialized_context.product) is Product assert len(deserialized_context.tracks) == 1 assert type(deserialized_context.tracks[0]) is Track assert deserialized_context.message_id == '236757' assert ( deserialized_context.message_thread_id == 'G010001997343X_XXX' ) assert deserialized_context.party_id == 'PADPIDA2007040502I' assert deserialized_context.product.vendor_id == 123123 assert deserialized_context.product.product_name == 'Scandinavian Woods' assert deserialized_context.product.release_type == 'EP' assert deserialized_context.product.metadata_language == 'ENG' assert deserialized_context.product.genres[0].genre == 'Country' assert deserialized_context.product.genres[0].subgenre == 'R and B sub' assert deserialized_context.product.p_line == \ '2010 Sony Music Entertainment' assert deserialized_context.product.c_line == \ '2010 Sony Music Entertainment' assert deserialized_context.update_indicator == 'OriginalMessage' assert deserialized_context.product.original_release_date == '2015-01-06' assert deserialized_context.product.product_version == 'New Version' assert deserialized_context.product.display_artists[0].name == \ 'Scandi Girls' assert \ deserialized_context.product.display_artists[0].sequence_number == 1 assert ( deserialized_context.product.display_artists[0].roles[0] == 'MainArtist' ) assert deserialized_context.product.marketing_blurb == \ 'A tagline to sell the Product can go here.' assert deserialized_context.product.imprint == 'BNA Records Label' assert deserialized_context.product.not_for_distribution == 'N' assert deserialized_context.product.special_instructions == 'some instros' assert deserialized_context.product.product_version_notes == 'some notes' assert deserialized_context.tracks[0].track_name == "Daniel's Theme" product_store = deserialized_context.product.stores[0] assert type(product_store) is Store assert product_store.store_id == 'spotify' assert product_store.link == 'spotify:album:368TKDyiyzFTwCyHJ0uWqc' assert product_store.delivery_date == '2020-12-03' assert deserialized_context.product.stores[0].carved_out is False assert deserialized_context.product.stores[1].carved_out is True assert len(deserialized_context.deals[0].deal_terms[0].commercial_model_types) == 1 # noqa assert deserialized_context.deals[0].deal_terms[0].price_type == '12' def test_incomplete_ddex_schema_deserialize(ddex_missing_fields): """Test deseralizing a DDEX document with missing required fields.""" deserialized_context = DDEXSchema().load(ddex_missing_fields) assert not deserialized_context.message_id assert not deserialized_context.party_id deal_term = deserialized_context.deals[0].deal_terms[0] assert not deal_term.commercial_model_types assert not deal_term.usage_type deal = deserialized_context.deals[1] assert not deal.release_references assert not deal.deal_terms track = deserialized_context.tracks[0] assert not track.release_reference assert not track.sequence_number assert not track.volume assert not track.track_name assert not track.resource_reference product = deserialized_context.product assert not product.genres[0].genre assert not product.release_reference assert not product.product_name assert product.display_artists[0].name == 'Jonas Hechmann Gejl' def test_ddex_schema_deserialize_missing_release_type(ddex_missing_fields): """Test deseralizing a DDEX document with missing required fields.""" ddex_missing_fields['ernm:NewReleaseMessage']['ReleaseList']['Release'][1][ 'ReleaseType'] = None with pytest.raises(ValidationError): DDEXSchema().load(ddex_missing_fields) def test_ddex_schema_deserialize_single_with_no_assets( ddex_document_single_no_assets): """Test deseralizing DDEX document representing a single into context.""" deserialized_context = DDEXSchema().load(ddex_document_single_no_assets) assert type(deserialized_context.product) is Product assert not deserialized_context.product.artwork assert len(deserialized_context.tracks) == 1 assert type(deserialized_context.tracks[0]) is Track track = deserialized_context.tracks[0] assert not track.asset assert deserialized_context.message_id == '236757' assert ( deserialized_context.message_thread_id == 'G010001997343X_XXX' ) assert deserialized_context.update_indicator == 'OriginalMessage' assert deserialized_context.product.imprint == 'BNA Records Label' def test_ddex_schema_deserialize_single_with_asset_and_preview( ddex_document_single_with_asset_preview): """Test deseralizing DDEX document representing a single into context.""" deserialized_context = DDEXSchema().load( ddex_document_single_with_asset_preview ) artwork = deserialized_context.product.artwork product = deserialized_context.product assert type(deserialized_context.product) is Product assert deserialized_context.product.artwork assert product.upc == '886444545099' assert artwork.filename == '1.jpg' assert artwork.filepath == 'resources/' assert len(deserialized_context.tracks) == 1 assert type(deserialized_context.tracks[0]) is Track track = deserialized_context.tracks[0] assert track.isrc == 'THBEC0000273' assert track.asset asset = track.asset assert asset.filename == '1.flac' assert asset.filepath == 'resources/' assert deserialized_context.message_id == '196785206' assert ( deserialized_context.message_thread_id == 'G010003140208H_TOC' ) assert deserialized_context.update_indicator == 'OriginalMessage' def test_ddex_schema_deserialize_with_multiple_release_details_by_territory( ddex_document_with_multiple_release_details): """Test deseralizing DDEX document with multiple release details.""" deserialized_context = DDEXSchema().load( ddex_document_with_multiple_release_details ) artwork = deserialized_context.product.artwork product = deserialized_context.product assert type(deserialized_context.product) is Product assert deserialized_context.product.artwork assert product.upc == '886447056493' assert product.display_artist_name == 'C. Tangana' assert product.major_label == 'Sony Music Entertainment Espana S.L.' assert artwork.filename == 'A10301A0003914291X_T-1219012743254_Image.jpg' assert artwork.filepath == 'resources/' assert len(deserialized_context.tracks) == 10 assert type(deserialized_context.tracks[0]) is Track track = deserialized_context.tracks[0] assert track.isrc == 'ES5021800052' assert track.asset asset = track.asset assert ( asset.filename == 'A10301A0003914291X_T-1102312743349_SoundRecording_001-001.flac' ) assert asset.filepath == 'resources/' assert deserialized_context.message_id == '196785220' assert ( deserialized_context.message_thread_id == 'G010003914291X_TOC' ) assert deserialized_context.update_indicator == 'OriginalMessage' assert product.duration == 'PT0H23M19S' def test_ddex_schema_deserialize_with_multiple_release_details_by_territory_not_worldwide( # noqa ddex_document_with_multiple_release_details_not_worldwide): """Test deseralizing DDEX document with multiple release details.""" deserialized_context = DDEXSchema().load( ddex_document_with_multiple_release_details_not_worldwide ) artwork = deserialized_context.product.artwork product = deserialized_context.product assert type(deserialized_context.product) is Product assert deserialized_context.product.artwork assert product.upc == '886447056493' assert product.display_artist_name == 'C. Tangana' assert product.major_label == 'Sony Music Entertainment Espana S.L.' assert artwork.filename == 'A10301A0003914291X_T-1219012743254_Image.jpg' assert artwork.filepath == 'resources/' assert len(deserialized_context.tracks) == 10 assert type(deserialized_context.tracks[0]) is Track track = deserialized_context.tracks[0] assert track.isrc == 'ES5021800052' assert track.asset asset = track.asset assert ( asset.filename == 'A10301A0003914291X_T-1102312743349_SoundRecording_001-001.flac' ) assert asset.filepath == 'resources/' assert deserialized_context.message_id == '196785220' assert ( deserialized_context.message_thread_id == 'G010003914291X_TOC' ) assert deserialized_context.update_indicator == 'OriginalMessage' assert product.duration == 'PT0H23M19S' def test_ddex_schema_deserialize_classical( ddex_document_classical): """Test deseralizing classical DDEX document.""" deserialized_context = DDEXSchema().load( ddex_document_classical ) artwork = deserialized_context.product.artwork product = deserialized_context.product assert type(deserialized_context.product) is Product assert deserialized_context.product.artwork assert product.upc == '886445714562' assert artwork.filename == 'A10301A0003476861G_T-121908652748_Image.jpg' assert artwork.filepath == 'resources/' assert len(deserialized_context.tracks) == 20 assert type(deserialized_context.tracks[0]) is Track track = deserialized_context.tracks[0] assert track.isrc == 'DEE861600236' assert track.release_reference == 'R1' assert track.sequence_number == 1 assert track.volume == 1 assert track.asset asset = track.asset assert asset.filename == \ 'A10301A0003476861G_T-110238630051_SoundRecording_001-001.flac' assert asset.filepath == 'resources/' # Check if a classical nested track has correct data nested_track = deserialized_context.tracks[6] assert nested_track.isrc == 'DEE861600242' assert nested_track.release_reference == 'R7' assert nested_track.sequence_number == 7 assert nested_track.volume == 1 assert nested_track.asset nested_track_asset = nested_track.asset assert nested_track_asset.filename == \ 'A10301A0003476861G_T-110238630057_SoundRecording_001-007.flac' assert nested_track_asset.filepath == 'resources/' assert deserialized_context.message_id == '200921520' assert ( deserialized_context.message_thread_id == 'G010003476861G_TOC' ) assert deserialized_context.update_indicator == 'OriginalMessage' def test_ddex_schema_deserialize_classical_with_deeply_nested_resource_groups( ddex_document_classical_deeply_nested_groups): """Test deseralizing classical DDEX document.""" deserialized_context = DDEXSchema().load( ddex_document_classical_deeply_nested_groups ) artwork = deserialized_context.product.artwork product = deserialized_context.product assert type(deserialized_context.product) is Product assert deserialized_context.product.artwork assert product.upc == '886445763089' assert artwork.filename == 'A10301A0003492512L_T-121908659390_Image.jpg' assert artwork.filepath == 'resources/' assert len(deserialized_context.tracks) == 11 assert type(deserialized_context.tracks[0]) is Track track = deserialized_context.tracks[0] assert track.isrc == 'USSM11600999' assert track.release_reference == 'R1' assert track.sequence_number == 1 assert track.volume == 1 assert track.asset asset = track.asset assert asset.filename == \ 'A10301A0003492512L_T-110239790445_SoundRecording_001-001.flac' assert asset.filepath == 'resources/' assert deserialized_context.message_id == '200921503' assert ( deserialized_context.message_thread_id == 'G010003492512L_TOC' ) assert deserialized_context.update_indicator == 'OriginalMessage' assert deserialized_context.product.original_release_date == '2016-06-03' def test_ddex_schema_deserialize_classical_with_nested_resource_group_lists( ddex_document_classical_deeply_nested_resource_group_lists): """Test deseralizing classical DDEX document.""" deserialized_context = DDEXSchema().load( ddex_document_classical_deeply_nested_resource_group_lists ) artwork = deserialized_context.product.artwork product = deserialized_context.product assert type(deserialized_context.product) is Product assert deserialized_context.product.artwork assert product.upc == '886445725452' assert artwork.filename == 'A10301A0003480299Y_T-121908540455_Image.jpg' assert artwork.filepath == 'resources/' assert len(deserialized_context.tracks) == 17 assert type(deserialized_context.tracks[0]) is Track track = deserialized_context.tracks[0] assert track.isrc == 'USSM11509632' assert track.release_reference == 'R1' assert track.sequence_number == 1 assert track.volume == 1 assert track.asset asset = track.asset assert asset.filename == \ 'A10301A0003480299Y_T-110238505192_SoundRecording_001-001.flac' assert asset.filepath == 'resources/' assert deserialized_context.message_id == '200921544' assert ( deserialized_context.message_thread_id == 'G010003480299Y_TOC' ) assert deserialized_context.update_indicator == 'OriginalMessage' assert ( deserialized_context.product.display_artists[0].roles[1] == 'Violin' ) @pytest.mark.parametrize('doc,expected', [ ('ddex_document', { 'upc': '886448369561', 'filename': 'A10301A0004280500R_T-1205814372821_Image.tif', 'filepath': 'resources/' }) ]) def test_ddex_schema_deserialize_product_information(doc, expected, request): """Test deseralizing DDEX document into context dict with objects.""" deserialized_context = DDEXSchema().load(request.getfixturevalue(doc)) product = deserialized_context.product assert product.upc == expected['upc'] assert product.is_main_release assert product.release_type == 'Album' assert not product.product_id assert product.artwork.filename == expected['filename'] assert product.artwork.filepath == expected['filepath'] @pytest.mark.parametrize('doc,expected', [ ('ddex_document', { 'isrc': 'USSM12001700', 'filename': 'A10301A0004280500R_T-1102314362750_SoundRecording_001-002.flac', 'filepath': 'resources/' }) ]) def test_ddex_schema_deserialize_track_information(doc, expected, request): """Test deseralizing DDEX document into context dict with objects.""" deserialized_context = DDEXSchema().load(request.getfixturevalue(doc)) track = deserialized_context.tracks[1] assert track.isrc == expected['isrc'] assert track.volume == 1 assert track.asset.filename == expected['filename'] assert track.asset.filepath == expected['filepath'] assert track.release_type == 'TrackRelease' assert not track.tuid # As we have not got the Orchard ID yet assert track.resource_reference == 'A2' @pytest.mark.parametrize('document,expected', [ ('ddex_document', { 'track_name': 'THE BEACH', 'track_version': None, 'track_p_line': '2020 Epic Records, a division of Sony Music Entertainment', 'artist_name': 'Giveon', 'artist_roles': [ 'AssociatedPerformer', 'BackgroundVocal', 'LeadVocalist', 'MainArtist' ], 'contributor_name': 'Giveon Evans', 'contributor_sequence_number': 1, 'contributor_roles': ['Arranger', 'Composer', 'Lyricist'], 'contributors_count': 9, 'localized_titles_count': 0, 'preview_start_time': 49, 'is_instrumental': True, }) ]) def test_ddex_schema_deserialize_track_metadata(document, expected, request): """Test deseralizing DDEX document into context dict with objects.""" deserialized_context = DDEXSchema().load(request.getfixturevalue(document)) deserialized_track = deserialized_context.tracks[0] assert deserialized_track.track_name == expected['track_name'] assert deserialized_track.track_version == expected['track_version'] assert deserialized_track.lyrics_language == 'ENG' assert deserialized_track.explicit == 'N' assert deserialized_track.p_line == expected['track_p_line'] assert deserialized_track.lyrics is None assert deserialized_track.ownership_rights is None assert deserialized_track.recording_country_code is None assert deserialized_track.us_publishing_obligation is None assert deserialized_track.publishers is None assert \ deserialized_track.display_artists[0].name == expected['artist_name'] assert \ deserialized_track.display_artists[0].sequence_number == 1 assert \ deserialized_track.display_artists[0].apple_id is None assert ( deserialized_track.display_artists[0].spotify_uri == 'spotify:artist:3Nrfpe0tUJi4K4DXYWgMUX') assert ( deserialized_track.display_artists[0].roles == expected['artist_roles'] ) assert ( deserialized_track.resource_contributors[0].name == expected['contributor_name'] ) assert ( deserialized_track.resource_contributors[0]. sequence_number == expected['contributor_sequence_number'] ) assert ( deserialized_track.resource_contributors[0].roles == expected['contributor_roles']) assert ( deserialized_track.resource_contributors[0].apple_id is None ) assert ( deserialized_track.resource_contributors[0].spotify_uri == 'spotify:artist:3Nrfpe0tUJi4K4DXYWgMUY') assert len(deserialized_track.resource_contributors) \ == expected['contributors_count'] assert len(deserialized_track.localized_titles) \ == expected['localized_titles_count'] assert deserialized_track.preview_start_time \ == expected['preview_start_time'] assert deserialized_track.is_instrumental == expected['is_instrumental'] def test_ddex_schema_deserialize_extended_track(ddex_combined_metadata): """Test deseralizing DDEX document into context dict with objects.""" deserialized_context = DDEXSchema().load(ddex_combined_metadata) deserialized_track = deserialized_context.tracks[0] assert deserialized_track.track_name == "Daniel's Theme" assert deserialized_track.isrc == 'QM7281702754' assert deserialized_track.ownership_rights == 'LICENSED' assert deserialized_track.recording_country_code == 'US' assert deserialized_track.copyright_owner_country == 'US' assert deserialized_track.us_publishing_obligation == 'Composition' assert deserialized_track.publishers == [ 'ATV Music Publishing', 'Chateau Publishing' ] assert deserialized_track.lyrics == 'Allow me to introduce myself...' assert deserialized_track.content_type == 'Music with vocals' assert deserialized_track.offer_type == 'ALL' def test_ddex_schema_deserialize_extended_single_track(ddex_combined_metadata): """Test deseralizing DDEX document with single track.""" ddex_combined_metadata.get('ernm:NewReleaseMessage') \ .get('Tracks').get('Track')[1] = {} deserialized_context = DDEXSchema().load(ddex_combined_metadata) deserialized_track = deserialized_context.tracks[0] assert deserialized_track.track_name == "Daniel's Theme" assert deserialized_track.isrc == 'QM7281702754' assert deserialized_track.ownership_rights == 'LICENSED' assert deserialized_track.recording_country_code == 'US' assert deserialized_track.copyright_owner_country == 'US' assert deserialized_track.us_publishing_obligation == 'Composition' assert deserialized_track.publishers == [ 'ATV Music Publishing', 'Chateau Publishing' ] assert deserialized_track.lyrics == 'Allow me to introduce myself...' def test_ddex_get_main_product(ddex_document_release_list): """Get main product should be able to parse out main product release.""" output = DDEXSchema().get_main_product(ddex_document_release_list) assert output.get('@IsMainRelease') @pytest.mark.parametrize('document,expected', [ ('ddex_document', {'tracks': 8}) ]) def test_ddex_get_tracks(document, expected, request): """Should be able to get a list of tracks.""" ddex_document = get_root_element(request.getfixturevalue(document)) release_list = \ ddex_document['ReleaseList']['Release'] sound_recordings = ddex_document['ResourceList']['SoundRecording'] output = DDEXSchema().get_tracks( ddex_document, release_list, sound_recordings, {}, 'en' ) assert len(output) == expected['tracks'] @pytest.mark.parametrize('document,expected', [ ('ddex_document', { 'filename': 'A10301A0004280500R_T-1102314362750_SoundRecording_001-002.flac' }) ]) def test_ddex_get_asset(document, expected, request): """Should be able to grab an asset file by resource reference of Track.""" ddex_document = get_root_element(request.getfixturevalue(document)) track = { 'ReleaseResourceReferenceList': { 'ReleaseResourceReference': {'#text': 'A2'}, } } output = DDEXSchema().get_track_asset(ddex_document, track) assert ( output['FileName'] == expected['filename'] ) @pytest.mark.parametrize( 'document', ['ddex_document'] ) def test_ddex_get_track_sequence(document, request): """Should be able to grab Track sequence number.""" ddex_document = get_root_element(request.getfixturevalue(document)) track = { 'ReleaseResourceReferenceList': { 'ReleaseResourceReference': {'#text': 'A2'}, } } output = DDEXSchema().get_track_sequence(ddex_document, track) assert output == '2' @pytest.mark.parametrize( 'document', ['ddex_document'] ) def test_ddex_get_track_side(document, request): """Should be able to grab Track side number.""" ddex_document = get_root_element(request.getfixturevalue(document)) track = { 'ReleaseResourceReferenceList': { 'ReleaseResourceReference': {'#text': 'A2'}, } } output = DDEXSchema().get_track_side(ddex_document, track) assert output == '1' def test_ddex_get_videos(ddex_video_document): """Should be able to get a list of videos.""" release_list = \ ddex_video_document['ernm:NewReleaseMessage']['ReleaseList']['Release'] videos = ddex_video_document[ 'ernm:NewReleaseMessage']['ResourceList']['Video'] output = DDEXSchema().get_video( ddex_video_document, release_list, videos, None ) assert type(output) is dict def test_ddex_video_schema_deserialize(ddex_video_document): """Test deseralizing DDEX video document into context dict with objects.""" deserialized_context = DDEXSchema().load(ddex_video_document) assert type(deserialized_context.product) is Product assert len(deserialized_context.tracks) == 0 assert type(deserialized_context.video) is Video assert deserialized_context.message_id == '196785218' assert deserialized_context.message_thread_id == 'G010000025264A_TOC' assert deserialized_context.product.product_name == 'Before Your Love' assert deserialized_context.product.genres[0].genre == 'Pop' assert deserialized_context.product.p_line == '2002 19 Recordings Limited' assert deserialized_context.product.c_line == '2002 19 Recordings Limited' assert deserialized_context.update_indicator == 'OriginalMessage' assert deserialized_context.product.original_release_date == '2004-01-08' assert deserialized_context.product.product_version == 'VIDEO' assert deserialized_context.product.display_artists[0].name == \ 'Kelly Clarkson' assert ( deserialized_context.product.display_artists[0].roles[0] == 'MainArtist' ) assert deserialized_context.video.display_artists[0].name == \ 'Kelly Clarkson' assert ( deserialized_context.video.display_artists[0].roles[0] == 'AssociatedPerformer' ) assert deserialized_context.video.resource_contributors[0].name == \ 'Robert Mayes' assert ( deserialized_context.video.resource_contributors[0].roles[0] == 'Composer' ) assert deserialized_context.video.video_name == 'Before Your Love' assert deserialized_context.video.video_version == 'VIDEO' assert len(deserialized_context.video.assets) == 2 assert deserialized_context.video.assets[0].aspect_ratio == '1.271' assert deserialized_context.video.assets[1].aspect_ratio == '1.333' assert deserialized_context.video.title_language == 'ENG' assert deserialized_context.video.content_language == 'ENG' def test_ddex_video_metadata_deserialize( ddex_video_with_related_audio_document): """Test deseralizing DDEX video metadata into context dict with objects.""" deserialized_context = DDEXSchema().load( ddex_video_with_related_audio_document) assert deserialized_context.video.video_name == 'Destan' assert deserialized_context.video.video_version is None assert deserialized_context.video.title_language == 'ENG' # This DDEX has no language of performance assert deserialized_context.video.content_language is None assert deserialized_context.video.product_code == '193483327570' assert deserialized_context.video.imprint == 'SG Productions' assert deserialized_context.video.video_type == 'Official Music Video' assert deserialized_context.video.p_line.line == 'SG PRODUCTIONS' assert deserialized_context.video.p_line.year == 2018 assert deserialized_context.video.c_line.line == 'SG Productions' assert deserialized_context.video.c_line.year == 2018 assert deserialized_context.video.genres[0].genre == 'Pop' assert deserialized_context.video.associated_track_isrc == 'TRAIM1800040' assert deserialized_context.video.description assert deserialized_context.video.parental_advisory == 'No' assert len(deserialized_context.video.keywords) == 10 assert deserialized_context.video.keywords[9] == 'MainReleaseKeyword' def test_ddex_video_with_user_defined_video_type( ddex_video_with_user_defined_video_type): """Test deseralizing DDEX video with user defined video type.""" deserialized_context = DDEXSchema().load( ddex_video_with_user_defined_video_type) assert deserialized_context.video.video_name == 'Tao Ren Yan De Zi' assert deserialized_context.video.video_version == 'Live' assert deserialized_context.video.title_language == 'ENG' assert deserialized_context.video.content_language == 'CHI' assert deserialized_context.video.product_code == 'G0100028912322' assert deserialized_context.video.imprint == 'Columbia' assert deserialized_context.video.video_type == 'Live Performance' assert deserialized_context.video.p_line.line == 'Sony Music Entertainment Taiwan Ltd.' # noqa assert deserialized_context.video.p_line.year == 2012 assert deserialized_context.video.c_line.line == 'Sony Music Entertainment Taiwan Ltd.' # noqa assert deserialized_context.video.c_line.year == 2012 assert deserialized_context.video.genres[0].genre == 'Chinese Pop/Rock' assert not deserialized_context.video.associated_track_isrc assert not deserialized_context.video.description assert deserialized_context.video.parental_advisory == 'Clean Version' def test_ddex_extended_project_data_deserialize(ddex_combined_metadata): """Test deserializing DDEX combined document into context dict.""" deserialized_context = DDEXSchema().load(ddex_combined_metadata) first_highlight = deserialized_context.project.marketing_highlights[0] store_highlights = deserialized_context.project.marketing_highlights[2] project_artist = deserialized_context.project.artist assert type(deserialized_context.project) is Project assert deserialized_context.project.description == \ 'The project description text will go here' assert deserialized_context.project.name == \ 'HIGHER LEARNING MUSIC FROM THE MOTION PICTURE' assert deserialized_context.project.project_code == '1001247' assert type(first_highlight) is MarketingHighlight assert first_highlight.territory_codes == ['US', 'CA'] assert first_highlight.highlight == 'marketing highlight enter here' assert store_highlights.store_codes == ['apple', 'spotify'] assert type(project_artist) is Participant assert project_artist.name == 'Laureano Brizuela' assert project_artist.spotify_uri == \ 'spotify:artist:6vWDO969PvNqNYHIOW5v0m' assert project_artist.apple_id == '13452345' def test_extended_project_no_artist_ids(ddex_combined_metadata): """Test that artist is deserialized appropriately with no artist ids.""" artist = { 'Name': 'Artist name' } ddex_combined_metadata['ernm:NewReleaseMessage']['Project']['Artist'] = \ artist deserialized_context = DDEXSchema().load(ddex_combined_metadata) assert deserialized_context.project.artist.spotify_uri is None assert deserialized_context.project.artist.apple_id is None def test_extended_project_one_artist_id(ddex_combined_metadata): """Test that artist is deserialized appropriately with one artist id.""" artist = { 'Name': 'Artist name', 'ArtistId': [ { '@Namespace': 'Spotify', '#text': 'spotify:artist:6vWDO969PvNqNYHIOW5v0m' } ] } ddex_combined_metadata['ernm:NewReleaseMessage']['Project']['Artist'] = \ artist deserialized_context = DDEXSchema().load(ddex_combined_metadata) assert deserialized_context.project.artist.spotify_uri == \ 'spotify:artist:6vWDO969PvNqNYHIOW5v0m' def test_ddex_schema_deserialize_with_artist_profile_page( ddex_video_with_artist_profile_document): """Test deseralizing DDEX document with artist profile page.""" deserialized_context = DDEXSchema().load( ddex_video_with_artist_profile_document) product = deserialized_context.product assert product.artist_profile_page == 'AudreyVEVO' def test_ddex_schema_deserialize_with_filtered_invalid_deal_term( ddex_with_invalid_deal_term_fields): """Test deseralizing DDEX that filters deal terms without start dates.""" deserialized_context = DDEXSchema().load( ddex_with_invalid_deal_term_fields) assert len(deserialized_context.deals) == 2, \ 'There should be 2 deals' assert len(deserialized_context.deals[0].deal_terms) == 1, \ 'The first deal (R0) should have a 1 valid deal terms' assert len(deserialized_context.deals[1].deal_terms) == 3, \ 'The second deal (R1) should have 3 valid deal terms' def test_ddex_schema_deserialize_track_localization( ddex_document_localized_data): """Test deseralizing DDEX document with localization data.""" deserialized_context = DDEXSchema().load(ddex_document_localized_data) deserialized_track = deserialized_context.tracks[0] assert len(deserialized_track.localized_titles) == 2 assert deserialized_track.localized_titles[0].language_code == 'RU' assert deserialized_track.localized_titles[0].title == \ 'Не позволяйте никому оборачивать вас' assert deserialized_track.localized_titles[0].version == 'Прямой эфир' assert deserialized_track.localized_titles[1].language_code == 'FR' assert deserialized_track.localized_titles[1].title == \ 'French Title' assert deserialized_track.localized_titles[1].version is None def test_ddex_schema_deserialize_track_artist_localization( ddex_document_localized_data): """Test deseralizing DDEX document with localization data.""" deserialized_context = DDEXSchema().load(ddex_document_localized_data) deserialized_track = deserialized_context.tracks[0] assert len(deserialized_track.display_artists[0].localized_names) == 2 assert deserialized_track.display_artists[0].localized_names[0].\ name == 'Albertina Walker' assert deserialized_track.display_artists[0].localized_names[0].\ language_code in ['RU', 'FR'] def test_ddex_schema_deserialize_product_localization( ddex_document_localized_data): """Test deseralizing DDEX document with localization data.""" deserialized_context = DDEXSchema().load(ddex_document_localized_data) deserialized_product = deserialized_context.product assert len(deserialized_product.localized_titles) == 2 assert deserialized_product.localized_titles[0].language_code == 'RU' assert deserialized_product.localized_titles[0].title == \ 'Песни Церкви - Живите в Мемфисе' assert deserialized_product.localized_titles[0].version is None assert deserialized_product.localized_titles[1].language_code == 'FR' assert deserialized_product.localized_titles[1].title == \ 'Songs Of The Church-Live In Memphis' assert deserialized_product.localized_titles[1].version is None def test_ddex_schema_deserialize_product_artist_localization( ddex_document_localized_artist): """Test deseralizing DDEX document with localization data.""" deserialized_context = DDEXSchema().load(ddex_document_localized_artist) deserialized_product = deserialized_context.product assert deserialized_product.display_artists[0].localized_names[0].\ language_code == 'RU' assert deserialized_product.display_artists[0].localized_names[0].\ name == 'Альбертина Уокер' assert deserialized_product.display_artists[0].localized_names[1].\ language_code == 'JP' assert deserialized_product.display_artists[0].localized_names[1].\ name == 'アルバーティナウォーカ' assert deserialized_product.display_artists[0].localized_names[2].\ language_code == 'FR' assert deserialized_product.display_artists[0].localized_names[2].\ name == 'Albertina Walker' assert len(deserialized_product.display_artists[0].localized_names) == 3 def test_ddex_schema_deserialize_duplicate_title_localization( ddex_document_localized_artist): """Test deseralizing DDEX document with duplicate localization data.""" ddex_document_localized_artist['ernm:NewReleaseMessage']['ReleaseList'][ 'Release'][0]['ReleaseDetailsByTerritory'][0]['Title'][2][ '@LanguageAndScriptCode'] = 'fr' with pytest.raises(Exception): DDEXSchema().load(ddex_document_localized_artist) def test_ddex_schema_deserialize_duplicate_artist_localization( ddex_document_localized_artist): """Test deseralizing DDEX document with duplicate localization data.""" ddex_document_localized_artist['ernm:NewReleaseMessage']['ReleaseList'][ 'Release'][0]['ReleaseDetailsByTerritory'][0]['DisplayArtist'][0][ 'PartyName'][2]['@LanguageAndScriptCode'] = 'jp' with pytest.raises(Exception): DDEXSchema().load(ddex_document_localized_artist) @pytest.mark.parametrize('test_input,expected', [ (['p_cl', None, None, None], 'p_cl'), ([None, 'p_pl', None, None], 'p_pl'), ([None, None, 't_cl', None], 't_cl'), ([None, None, None, 't_pl'], 't_pl'), (['p_cl', None, 't_cl', None], 'p_cl') ]) def test_ddex_schema_get_product_c_line( ddex_combined_metadata, test_input, expected): """Test that we choose the correct product c_line.""" assert DDEXSchema().get_product_c_line( test_input[0], test_input[1], test_input[2], test_input[3]) == expected def test_ddex_schema_serializes_deals(ddex_single_preorder): """Test deserializing DDEX document for Deals.""" deserialized_context = DDEXSchema().load(ddex_single_preorder) pre_order_deal = deserialized_context.deals[1].deal_terms[3] assert type(deserialized_context.deals[0]) is Deal assert type(pre_order_deal.pre_order) is bool assert pre_order_deal.pre_order is True assert pre_order_deal.release_display_date == '2021-04-20T00:00:00' assert pre_order_deal.track_listing_preview_date == '2021-04-20T00:00:00' assert pre_order_deal.cover_art_preview_date == '2021-04-20T00:00:00' assert pre_order_deal.clip_preview_date == '2021-04-30T00:00:00' def test_ddex_schema_instant_grat_deals(ddex_album_preorder_instant_grats): """Test deserializing DDEX document with instant grats.""" deserialized_context = DDEXSchema().load(ddex_album_preorder_instant_grats) instant_grats = \ deserialized_context.deals[0].deal_terms[1].instant_gratifications assert type(instant_grats) is InstantGratification assert instant_grats.references == ['A1', 'A2'] assert instant_grats.start_date_time == '2021-04-25T00:00:00' assert instant_grats.start_date == '2021-04-20' def test_ddex_schema_territory_codes(ddex_document): """Test deserializing DDEX document with territory codes.""" deserialized_context = DDEXSchema().load(ddex_document) territories = deserialized_context.deals[0].deal_terms[0].territories assert len(territories) == 83 assert territories[0] == 'AE' def test_ddex_schema_deserialize_without_project_arist( ddex_single_with_extended_no_project_artist): """Test deseralizing DDEX document without project artist field.""" deserialized_context = DDEXSchema().load( ddex_single_with_extended_no_project_artist) project = deserialized_context.project assert not project.artist def test_ddex_schema_deserialize_without_language_of_performance( ddex_single_without_language_of_performance): """Test DDEX document without lang of performance track field.""" deserialized_context = DDEXSchema().load( ddex_single_without_language_of_performance) track = deserialized_context.tracks[0] # Lyrics language is missing assert track.lyrics_language is None def test_ddex_schema_deserialize_with_multiple_sound_recording_territories( ddex_multiple_sound_recording_details_by_territory): """Test DDEX with multiple SoundRecordingDetailsByTerritory.""" deserialized_context = DDEXSchema().load( ddex_multiple_sound_recording_details_by_territory) track = deserialized_context.tracks[0] # Explicit field set correctly assert track.explicit == 'N' def test_ddex_schema_with_excluded_territories( ddex_single_with_excluded_territory): """Test DDEX with excluded territories.""" deserialized_context = DDEXSchema().load( ddex_single_with_excluded_territory) deal_term = deserialized_context.deals[0].deal_terms[0] assert deal_term.excluded_territories == ['AD', 'CA', 'ZA', 'ZM', 'ZW'] def test_ddex_schema_deserialize_ext_catalog_number(ddex_combined_metadata): """Test deserializing with the catalog number only in the extended meta.""" ddex_combined_metadata['ernm:NewReleaseMessage']['ReleaseList']['Release'][ 0]['ReleaseId'].pop('CatalogNumber', None) deserialized_context = DDEXSchema().load(ddex_combined_metadata) assert deserialized_context.product.catalog_number == 'G010001389594X' def test_ddex_schema_deserialize_apple_id(ddex_combined_metadata): """Test deserializing the apple id.""" deserialized_context = DDEXSchema().load(ddex_combined_metadata) assert deserialized_context.project.artist.apple_id == '13452345' ddex_combined_metadata['ernm:NewReleaseMessage']['Project']['Artist'][ 'ArtistId'][1]['@Namespace'] = 'Apple' deserialized_context = DDEXSchema().load(ddex_combined_metadata) assert deserialized_context.project.artist.apple_id == '13452345' ddex_combined_metadata['ernm:NewReleaseMessage']['Project']['Artist'][ 'ArtistId'][0]['@Namespace'] = 'Apple' deserialized_context = DDEXSchema().load(ddex_combined_metadata) assert deserialized_context.project.artist.apple_id == '13452345' def test_fluve_ddex_using_ddex_schema(ddex_fluve_multiple_tracks): """Test deserializing a Fluve vanilla DDEX.""" deserialized_context = DDEXSchema().load(ddex_fluve_multiple_tracks) assert deserialized_context.product assert len(deserialized_context.deals) > 0 assert len(deserialized_context.tracks) > 0 def test_different_track_title_language_localizations(som_livre_combined_ddex): """Test different track title language from product metadata language.""" deserialized_context = DDEXSchema().load(som_livre_combined_ddex) track = deserialized_context.tracks[3] assert track.isrc == 'BX7E52500074' assert track.display_artists[0].localized_names[0].language_code == 'EN' assert track.localized_titles[0].language_code == 'EN'