Skip to content

Commit

Permalink
letcture 13
Browse files Browse the repository at this point in the history
  • Loading branch information
mdhayath64 committed Jul 22, 2023
1 parent 7ae1a25 commit 651333a
Show file tree
Hide file tree
Showing 25 changed files with 329 additions and 21 deletions.
5 changes: 4 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,7 @@ Read+Django/music_app/music_controller/frontend/static/frontend/main.js
Read+Django/music_app/music_controller/frontend/static/frontend/main.js.LICENSE.txt
Read+Django/music_app/music_controller/api/__pycache__
Read+Django/music_app/music_controller/music_controller/__pycache__

Read+Django/music_app/music_controller/frontend/__pycache__
Read+Django/music_app/music_controller/sportify/__pycache__
Read+Django/music_app/music_controller/music_controller/__pycache__/
Read+Django/music_app/music_controller/frontend/__pycache__
1 change: 1 addition & 0 deletions Read+Django/References.txt
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ JavaScript (ES6) code snippets

installation (one time)
>> pip install django djangorestframework
>> pip install requests

create project
>> django-admin startproject <project_name>
Expand Down
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified Read+Django/music_app/music_controller/db.sqlite3
Binary file not shown.
Binary file not shown.
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import React, { Component } from "react";
import {Grid, Typography, Card, Iconbutton} from "@material-ui/core"
import { PlayArrwIcon, SkipNextIcon, PauseIcon} from "@material-ui/icons"

export default class MusicPlayer extends Component {
constructor(props) {
super(props);
}

render() {
return (
<Card>
<Grid container alignItems="certer">
<Grid item align="center" xs={4}>
<img src={this.props.image_url} height="100%" width="100%" />
</Grid>
<Grid item align="center" xs={8}>
<Typography color="textsecondary" variant="subtitle1">
{this.props.title}
</Typography>
<div>
<Iconbutton>
{this.props.is_playing ? <PauseIcon /> : <PlayArrwIcon />}
</Iconbutton>
</div>

</Grid>
</Grid>
</Card>
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,14 +10,26 @@ export default class Room extends Component {
guestCanPause: false,
isHost: false,
showSettings: false,
spotifyAuthenticated: false,
song: {}
};
this.roomCode = this.props.match.params.roomCode;
this.leaveButtonPressed = this.leaveButtonPressed.bind(this);
this.updateShowSettings = this.updateShowSettings.bind(this)
this.renderSettingButtton = this.renderSettingButtton.bind(this);
this.renderSettings = this.renderSettings.bind(this);
this.getRoomDetails = this.getRoomDetails.bind(this);
this.getRoomDetails();
this.authenticateSpotify = this.authenticateSpotify.bind(this);
this.getCurrentSong = this.getCurrentSong.bind(this);
this.getRoomDetails();
}

componentDidMount() {
this.interval = setInterval(this.getCurrentSong, 1000)
}

componentWillUnmount() {
clearInterval(this.interval)
}

getRoomDetails() {
Expand All @@ -35,9 +47,42 @@ export default class Room extends Component {
guestCanPause: data.guest_can_pause,
isHost: data.is_host,
});
if (this.state.isHost){
this.authenticateSpotify();
}
});
}

authenticateSpotify() {
fetch('/sportify/is-authenticated')
.then((response) => response.json())
.then((data) => {
this.setState({spotifyAuthenticated: data.status});
if(!data.status) {
fetch('/sportify/get-auth-url')
.then((response) => response.json())
.then((data) => {
window.location.replace(data.url);
});
}
});
}

getCurrentSong() {
fetch('/sportify/current-song')
.then((response) => {
if (!response.ok) {
return {};
} else {
return response.json();
}
})
.then((data) => {
this.setState({ song: data });
console.log(data);
});
}

leaveButtonPressed() {
const requestOption = {
method: "POST",
Expand Down Expand Up @@ -102,21 +147,10 @@ export default class Room extends Component {
Code: {this.roomCode}
</Typography>
</Grid>
<Grid item xs={12} align="center">
<Typography variant="h6" component="h6">
Votes: {this.state.votesToSkip}
</Typography>
</Grid>
<Grid item xs={12} align="center">
<Typography variant="h6" component="h6">
Guest Can Pause: {this.state.guestCanPause.toString()}
</Typography>
</Grid>
<Grid item xs={12} align="center">
<Typography variant="h6" component="h6">
Host: {this.state.isHost.toString()}
</Typography>
</Grid>

{/* {this.state.song} */}


{this.state.isHost ? this.renderSettingButtton() : null}
<Grid item xs={12} align="center">
<Button variant="contained" color="secondary" onClick={this.leaveButtonPressed} component={Link}>
Expand Down
4 changes: 3 additions & 1 deletion Read+Django/music_app/music_controller/frontend/urls.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
from django.urls import path
from .views import index

app_name = 'frontend'

urlpatterns = [
path('', index),
path('', index, name=''),
path('join', index),
path('create', index),
path('room/<str:roomCode>', index)
Expand Down
Binary file not shown.
Binary file not shown.
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@
DEBUG = True

ALLOWED_HOSTS = [
'192.168.0.112'
# '192.168.0.112'
]


Expand All @@ -41,7 +41,8 @@
'django.contrib.staticfiles',
'api.apps.ApiConfig',
'rest_framework',
'frontend.apps.FrontendConfig'
'frontend.apps.FrontendConfig',
'sportify.apps.SportifyConfig'
]

MIDDLEWARE = [
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,6 @@
urlpatterns = [
path('admin/', admin.site.urls),
path('api/', include('api.urls')),
path('', include('frontend.urls'))
path('', include('frontend.urls')),
path('sportify/', include('sportify.urls'))
]
Empty file.
3 changes: 3 additions & 0 deletions Read+Django/music_app/music_controller/sportify/admin.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.contrib import admin

# Register your models here.
6 changes: 6 additions & 0 deletions Read+Django/music_app/music_controller/sportify/apps.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from django.apps import AppConfig


class SportifyConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'sportify'
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
CLIENT_ID = "40ed5b29eda141e5a45038852ecf89a3"
CLIENT_SECRET = "17e4ba446a444aa0aa920bfdf79caa26"
REDIRECT_URI = "http://127.0.0.1:8000/sportify/redirect"
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# Generated by Django 4.2.1 on 2023-07-11 20:05

from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='SportifyToken',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('user', models.CharField(max_length=50, unique=True)),
('created_at', models.DateTimeField(auto_now_add=True)),
('refresh_token', models.CharField(max_length=150)),
('access_token', models.CharField(max_length=150)),
('expires_in', models.DateTimeField()),
('token_type', models.CharField(max_length=50)),
],
),
]
Empty file.
Binary file not shown.
Binary file not shown.
10 changes: 10 additions & 0 deletions Read+Django/music_app/music_controller/sportify/models.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
from django.db import models

# Create your models here.
class SportifyToken(models.Model):
user = models.CharField(max_length=50, unique=True)
created_at = models.DateTimeField(auto_now_add=True)
refresh_token = models.CharField(max_length=150)
access_token = models.CharField(max_length=150)
expires_in = models.DateTimeField()
token_type = models.CharField(max_length=50)
3 changes: 3 additions & 0 deletions Read+Django/music_app/music_controller/sportify/tests.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.test import TestCase

# Create your tests here.
9 changes: 9 additions & 0 deletions Read+Django/music_app/music_controller/sportify/urls.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
from django.urls import path
from .views import *

urlpatterns = [
path('get-auth-url', AuthURL.as_view()),
path('redirect', sportify_callback),
path('is-authenticated', IsAuthenticated.as_view()),
path('current-song', CurrentSong.as_view())
]
76 changes: 76 additions & 0 deletions Read+Django/music_app/music_controller/sportify/utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
from .models import SportifyToken
from django.utils import timezone
from datetime import timedelta
from .credentials import CLIENT_ID, CLIENT_SECRET
from requests import post, put, get

BASE_URL = "https://api.spotify.com/v1/me/"

def get_user_tokens(session_id):
user_tokens = SportifyToken.objects.filter(user = session_id)
if user_tokens.exists():
return user_tokens[0]
else:
return None

def update_or_create_token(session_id, access_token, token_type, expires_in, refresh_token):
tokens = get_user_tokens(session_id)
expires_in = timezone.now() + timedelta(seconds=expires_in)

if tokens:
tokens.access_token = access_token
tokens.refresh_token = refresh_token
tokens.expires_in = expires_in
tokens.token_type = token_type
tokens.save(update_fields=['access_token',
'refesh_toke', 'expires_in', 'token_type'])

else:
tokens = SportifyToken(user=session_id, access_token=access_token,
refresh_token=refresh_token, token_type=token_type, expires_in=expires_in)
tokens.save()

def is_spotify_authenticated(session_id):
tokens = get_user_tokens(session_id)
if tokens:
expiry = tokens.expires_in
if expiry <= timezone.now():
refresh_spotify_token(session_id)

return True

return False


def refresh_spotify_token(session_id):
refresh_token = get_user_tokens(session_id).refresh_token

response = post('https://accounts.spotify.com/api/token', data={
'grant_type': 'refresh_token',
'refresh_token': refresh_token,
'client_id': CLIENT_ID,
'client_secret': CLIENT_SECRET
}).json()

access_token = response.get('access_token')
token_type = response.get('token_type')
expires_in = response.get('expires_in')
refresh_token = response.get('refresh_token')

update_or_create_token(session_id, access_token, token_type, expires_in, refresh_token)

def execute_spotify_api_request(session_id, endpoint, post_=False, put_=False):
tokens = get_user_tokens(session_id)
headers = {'Content-Type': 'application/json',
'Authorization': "Bearer " + tokens.access_token}

if post_:
post(BASE_URL + endpoint, headers=headers)
if put_:
put(BASE_URL + endpoint, headers=headers)

response = get(BASE_URL + endpoint, {}, headers=headers)
try:
return response.json()
except:
return {'Error': 'Issue with request'}
Loading

0 comments on commit 651333a

Please sign in to comment.