示例#1
0
        public bool DeletePartyWithHost(PartyGoer host)
        {
            List <string> partyKeys = new List <string>();

            foreach (var key in _parties.Keys)
            {
                if (_parties[key].IsHost(host))
                {
                    partyKeys.Add(key);
                }
            }

            if (partyKeys.Count > 1)
            {
                throw new Exception($"Host: {host?.GetId()} is hosting {partyKeys.Count} parties. A host should only host 1 party at a time.");
            }

            if (partyKeys == null)
            {
                throw new Exception($"Host: {host?.GetId()} is not hosting a party");
            }

            _parties.Remove(partyKeys.First());

            return(true);
        }
示例#2
0
        public async Task <string> GetPartyGoerAccessTokenAsync(PartyGoer partyGoer)
        {
            if (await _spotifyAuthentication.DoesAccessTokenNeedRefreshAsync(partyGoer.GetId()))
            {
                await _spotifyHttpClient.RefreshTokenForUserAsync(partyGoer.GetId());
            }

            return(await _spotifyAuthentication.GetAccessTokenAsync(partyGoer));
        }
示例#3
0
        public async Task <HttpResponseMessage> SendHttpRequestAsync(PartyGoer user, SpotifyEndpoint spotifyEndpoint, ApiParameters queryStringParameters, object requestBodyParameters)
        {
            await RefreshTokenForUserAsync(user.GetId());

            string spotifyEndpointUrl = spotifyEndpoint.EndpointUrl;

            // look to see if spotifyendpoint has keys
            if (spotifyEndpoint?.Keys != null)
            {
                // we need to verify these keys exist in api parameters
                foreach (string key in spotifyEndpoint.Keys)
                {
                    if (!queryStringParameters.Keys.ContainsKey(key))
                    {
                        throw new Exception($"Endpoint: {spotifyEndpoint} says it contains a key: {key} but it is not found in parameters");
                    }

                    spotifyEndpointUrl = spotifyEndpointUrl.Replace(key, queryStringParameters.Keys[key]);
                }
            }

            using (var requestMessage = new HttpRequestMessage(spotifyEndpoint.HttpMethod, spotifyEndpointUrl + AddQueryStrings(queryStringParameters)))
            {
                requestMessage.Headers.Authorization = await _spotifyAuthentication.GetAuthenticationHeaderForPartyGoerAsync(user.GetId());

                if (requestBodyParameters != null)
                {
                    requestMessage.Content = new StringContent(JsonConvert.SerializeObject(requestBodyParameters));
                }

                return(await _httpClient.SendAsync(requestMessage));
            }
        }
示例#4
0
        public async Task <List <Device> > GetUserDevicesAsync(PartyGoer partyGoer)
        {
            HttpResponseMessage response = await SendHttpRequestAsync(partyGoer.GetId(), _apiEndpoints[ApiEndpointType.GetUserDevices]);

            if (response.IsSuccessStatusCode)
            {
                JObject json = JObject.Parse(await response.Content.ReadAsStringAsync());

                List <Device> devices = new List <Device>();
                foreach (var item in json["devices"])
                {
                    devices.Add(new Device
                    {
                        Name   = item["name"].ToString(),
                        Active = item["is_active"].Value <bool>(),
                        Id     = item["id"].ToString()
                    });
                }

                return(devices);
            }
            else
            {
                SpotifyApiException exception = new SpotifyApiException("Unable to get users devices from Spotify");

                await _logService.LogExceptionAsync(exception, await response.Content.ReadAsStringAsync());

                throw exception;
            }
        }
示例#5
0
        public async Task <IActionResult> Authorized(string code)
        {
            try
            {
                PartyGoer newUser = await _authenticationService.AuthenticateUserWithAccessCodeAsync(code);

                if (!newUser.HasPremium())
                {
                    // TODO: create this
                    return(RedirectToAction("NoPremium", "Error"));
                }

                // Get details from spotify of user
                var identity = new ClaimsIdentity(CookieAuthenticationDefaults.AuthenticationScheme);
                identity.AddClaim(new Claim(ClaimTypes.NameIdentifier, newUser.GetId()));

                var principal = new ClaimsPrincipal(identity);

                await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme, principal);

                await _logService.LogUserActivityAsync(newUser, "Successfully authenticated through Spotify");

                return(RedirectToAction("App", "Party"));
            }
            catch (Exception)
            {
                //  TODO: CHANGE THIS TO THE IDNEX PAGE ON HOME
                return(RedirectToAction("App", "Party"));
            }
        }
示例#6
0
        public bool LeaveParty(PartyGoer attendee)
        {
            List <string> partyKeys = new List <string>();

            foreach (var key in _parties.Keys)
            {
                if (_parties[key].IsListener(attendee))
                {
                    partyKeys.Add(key);
                }
            }

            if (partyKeys.Count > 1)
            {
                partyKeys.ForEach(p => _parties[p].LeaveParty(attendee));

                throw new PartyGoerWasInMultiplePartiesException($"The user {attendee} was in {partyKeys.Count} but was successfully removed from them");
            }

            if (partyKeys == null || partyKeys.Count == 0)
            {
                throw new Exception($"The attendee: {attendee.GetId()} is not currently in a party");
            }

            _parties[partyKeys.First()].LeaveParty(attendee);

            return(true);
        }
示例#7
0
        public void JoinParty(PartyGoer partyGoer)
        {
            _listeners.TryAdd(partyGoer.GetId(), partyGoer);

            if (_listeners.Count == 1)
            {
                _host = partyGoer;
            }
        }
示例#8
0
 public List <PartierContribution> GetContributions(PartyGoer partier)
 {
     return(_contributions.Where(p => p.ContributedBy == partier.GetId()).Select(p => new PartierContribution
     {
         Id = p.Id,
         ContributionId = p.ContributionId,
         Name = p.Name,
         Type = p.Type
     }).ToList());
 }
示例#9
0
        public async Task TogglePlaybackAsync(PartyGoer partyGoer)
        {
            // Grabbing partier by reference, so any change I make to it will change it in the list
            if (_listeners.TryGetValue(partyGoer.GetId(), out PartyGoer partier))
            {
                partier.ToggleMusicPlaybackState();

                await DomainEvents.RaiseAsync(new ToggleMusicState { Listener = partier, State = DeterminePlaybackState(partier.IsMusicPaused()) });
            }
        }
示例#10
0
        public async Task RemoveContributionAsync(string partyCode, PartyGoer partier, Guid contributionId)
        {
            Party party = await _partyRepository.GetPartyWithCodeAsync(partyCode);

            if (!party.IsListener(partier))
            {
                throw new Exception($"{partier.GetId()} is not part of party {partyCode} but tried to remove contribution {contributionId}");
            }

            party.RemoveContribution(partier, contributionId);
        }
示例#11
0
        public async Task <List <PartierContribution> > GetContributionsAsync(string partyCode, PartyGoer partier)
        {
            Party party = await _partyRepository.GetPartyWithCodeAsync(partyCode);

            if (!party.IsListener(partier))
            {
                throw new Exception($"{partier.GetId()} is not part of party {partyCode} but tried to get their contributions to that party");
            }

            return(await party.GetUserContributionsAsync(partier));
        }
示例#12
0
 public Party(PartyGoer host)
 {
     _host      = host;
     _listeners = new Dictionary <string, PartyGoer> {
         { host.GetId(), host }
     };
     _partyCode                   = GeneratePartyCode();
     _trackPositionTime           = new Stopwatch();
     _queue                       = new Queue();
     _history                     = new List <Track>();
     _nextTrackTimer              = new Timer(async(obj) => await NextTrackAsync());
     _usersThatDislikeCurrentSong = new List <PartyGoer>();
     _contributionManager         = new ContributionManager();
 }
示例#13
0
        public async Task <IActionResult> GetUserDetails()
        {
            PartyGoer currentUser = await _partyGoerService.GetCurrentPartyGoerAsync();

            Party party = await _partyService.GetPartyWithAttendeeAsync(currentUser);

            if (party != null)
            {
                return(Ok(new { IsInParty = true, Party = new { PartyCode = party.GetPartyCode() }, Details = new { Id = currentUser.GetId() } }));
            }
            else
            {
                return(Ok(new { IsInParty = false, UserDetails = new { Id = currentUser.GetId() } }));
            }
        }
示例#14
0
        public void LeaveParty(PartyGoer partyGoer)
        {
            _listeners.Remove(partyGoer.GetId());

            if (IsHost(partyGoer))
            {
                if (_listeners.Count > 0)
                {
                    _host = _listeners.First().Value;
                }
                else
                {
                    _host = null;
                }
            }
        }
示例#15
0
        public async Task <Domain.Errors.ServiceResult <UpdateSongError> > UpdateSongForPartyGoerAsync(PartyGoer partyGoer, List <string> songUris, int currentSongProgressInMs)
        {
            string perferredDeviceId = partyGoer.GetPerferredDeviceId();

            ApiParameters parameters = null;

            if (!string.IsNullOrWhiteSpace(perferredDeviceId))
            {
                parameters = new ApiParameters
                {
                    Parameters = new Dictionary <string, string>
                    {
                        { "device_id", perferredDeviceId }
                    }
                };
            }

            HttpResponseMessage response = null;

            if (parameters != null)
            {
                response = await SendHttpRequestAsync(partyGoer, _apiEndpoints[ApiEndpointType.PlaySong], parameters,
                                                      new StartUserPlaybackSong { uris = songUris.Select(song => song.Contains("spotify:track:") ? song : $"spotify:track:{song}".Split('+').First()).ToList(), position_ms = currentSongProgressInMs });
            }
            else
            {
                response = await SendHttpRequestAsync(partyGoer, _apiEndpoints[ApiEndpointType.PlaySong],
                                                      new StartUserPlaybackSong { uris = songUris.Select(song => song.Contains("spotify:track:") ? song : $"spotify:track:{song}".Split('+').First()).ToList(), position_ms = currentSongProgressInMs });
            }

            Domain.Errors.ServiceResult <UpdateSongError> error = new Domain.Errors.ServiceResult <UpdateSongError>();

            if (response.IsSuccessStatusCode)
            {
                return(error);
            }
            else
            {
                await _logService.LogExceptionAsync(new Exception($"Unable to update song for {partyGoer.GetId()}"), await response.Content.ReadAsStringAsync());

                // TODO: Check status codes and add specific messaging for status codes based on Spotifys API
                error.AddError(new UpdateSongError($"Unable to update song for {partyGoer.GetId()}"));
                return(error);
            }
        }
示例#16
0
 public Task <string> GetAccessTokenAsync(PartyGoer partyGoer)
 {
     return(Task.FromResult(AuthenticationTokens[partyGoer.GetId()].AccessToken));
 }
示例#17
0
 public async Task <HttpResponseMessage> SendHttpRequestAsync(PartyGoer user, SpotifyEndpoint spotifyEndpoint, object content = null, bool useQueryString = false)
 {
     return(await SendHttpRequestAsync(user.GetId(), spotifyEndpoint, content, useQueryString));
 }
示例#18
0
 public bool IsListener(PartyGoer listenerInQuestion)
 {
     return(_listeners.ContainsKey(listenerInQuestion.GetId()));
 }
示例#19
0
 public void RemoveContribution(PartyGoer partier, Guid contributionId)
 {
     _contributions.RemoveAll(p => p.ContributedBy == partier.GetId() && p.ContributionId == contributionId);
 }
示例#20
0
 public async Task LogUserActivityAsync(PartyGoer user, string activity)
 {
     await _repository.LogUserActivityAsync(user.GetId(), activity);
 }
示例#21
0
        public async Task <IActionResult> RemoveUserContribution(string partyCode, Guid contributionId)
        {
            PartyGoer partier = await _partyGoerService.GetCurrentPartyGoerAsync();

            try
            {
                await _partyService.RemoveContributionAsync(partyCode, partier, contributionId);

                return(StatusCode(200));
            }
            catch (Exception ex)
            {
                await _logService.LogExceptionAsync(ex, $"Failed to remove contribution {contributionId} for user {partier.GetId()}");

                return(StatusCode(500));
            }
        }
示例#22
0
        public async Task ConnectToParty(string partyCode)
        {
            PartyGoer partier = await _partyGoerService.GetCurrentPartyGoerAsync();

            if (!await _partyService.IsUserPartyingAsync(partier) && !await _partyService.IsUserHostingAPartyAsync(partier))
            {
                await _partyService.JoinPartyAsync(new Domain.DTO.PartyCodeDTO {
                    PartyCode = partyCode
                }, partier);

                await Groups.AddToGroupAsync(Context.ConnectionId, partyCode);

                await Clients.Group(partyCode).SendAsync("UpdateParty", $"{Context.UserIdentifier} has joined the party {partyCode}");
            }

            // Add the partier to real-time connection group
            await Groups.AddToGroupAsync(Context.ConnectionId, partyCode);

            await Clients.GroupExcept(partyCode, new List <string> {
                Context.ConnectionId
            }).SendAsync("NewListener", Context.UserIdentifier);

            Party party = await _partyService.GetPartyWithAttendeeAsync(partier);

            // Update the view of the partier to the current playlist
            await Clients.Client(Context.ConnectionId).SendAsync("InitialPartyLoad",
                                                                 new
            {
                Song     = party.GetCurrentSong(),
                Position = party.GetCurrentPositionInSong()
            },
                                                                 party.GetHistory(),
                                                                 party.GetQueue(),
                                                                 new
            {
                PartyCode = party.GetPartyCode(),
                Listeners = ConvertToListenerModel(party.GetListeners()),
                Host      = party.GetHost().GetId()
            }
                                                                 );;

            // check for explicit music
            if (!partier.CanListenToExplicitSongs() && party.HasExplicitTracks())
            {
                await Clients.Client(Context.ConnectionId).SendAsync("ExplicitSong", "You have filtering explicit music turned on in Spotify and there are explicit songs in the queue. We will not play the explicit song for you but continue playback when a non explicit song comes on.");
            }

            await Clients.Client(Context.ConnectionId).SendAsync("InitializeWebPlayer", await _partyGoerService.GetPartyGoerAccessTokenAsync(partier));

            // make sure that the users spotify is connected
            if (string.IsNullOrEmpty(await _spotifyHttpClient.GetUsersActiveDeviceAsync(partier.GetId())))
            {
                await Clients.Client(Context.ConnectionId).SendAsync("ConnectSpotify", "");
            }

            await _logService.LogUserActivityAsync(partier, $"Joined real time collobration in party with code {partyCode}");

            return;
        }