mirror of
https://github.com/spl0k/supysonic.git
synced 2024-12-23 01:16:18 +00:00
Merge pull request #24 from jelmer/setup
Move supysonic into its own package, and add a setup file.
This commit is contained in:
commit
71a82d76b2
4
.gitignore
vendored
4
.gitignore
vendored
@ -1,2 +1,6 @@
|
|||||||
*.pyc
|
*.pyc
|
||||||
*.swp
|
*.swp
|
||||||
|
*~
|
||||||
|
build/
|
||||||
|
dist/
|
||||||
|
MANIFEST
|
||||||
|
1
MANIFEST.in
Normal file
1
MANIFEST.in
Normal file
@ -0,0 +1 @@
|
|||||||
|
include README.md
|
@ -20,7 +20,7 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
import sys, cmd, argparse, getpass, time
|
import sys, cmd, argparse, getpass, time
|
||||||
import config
|
from supysonic import config
|
||||||
|
|
||||||
class CLIParser(argparse.ArgumentParser):
|
class CLIParser(argparse.ArgumentParser):
|
||||||
def error(self, message):
|
def error(self, message):
|
||||||
@ -219,12 +219,12 @@ if __name__ == "__main__":
|
|||||||
if not config.check():
|
if not config.check():
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
|
|
||||||
import db
|
from supysonic import db
|
||||||
db.init_db()
|
db.init_db()
|
||||||
|
|
||||||
from managers.folder import FolderManager
|
from supysonic.managers.folder import FolderManager
|
||||||
from managers.user import UserManager
|
from supysonic.managers.user import UserManager
|
||||||
from scanner import Scanner
|
from supysonic.scanner import Scanner
|
||||||
|
|
||||||
if len(sys.argv) > 1:
|
if len(sys.argv) > 1:
|
||||||
CLI().onecmd(' '.join(sys.argv[1:]))
|
CLI().onecmd(' '.join(sys.argv[1:]))
|
@ -22,7 +22,7 @@
|
|||||||
import sys
|
import sys
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
from web import create_application
|
from supysonic.web import create_application
|
||||||
|
|
||||||
app = create_application()
|
app = create_application()
|
||||||
if app:
|
if app:
|
||||||
|
31
setup.py
Executable file
31
setup.py
Executable file
@ -0,0 +1,31 @@
|
|||||||
|
#!/usr/bin/python
|
||||||
|
# encoding: utf-8
|
||||||
|
|
||||||
|
from distutils.core import setup
|
||||||
|
|
||||||
|
setup(name='supysonic',
|
||||||
|
description='Python implementation of the Subsonic server API.',
|
||||||
|
keywords='subsonic music',
|
||||||
|
version='0.1',
|
||||||
|
url='https://github.com/spl0k/supysonic',
|
||||||
|
license='AGPLv3',
|
||||||
|
author='Alban Féron',
|
||||||
|
author_email='alban.feron@gmail.com',
|
||||||
|
long_description="""
|
||||||
|
Supysonic is a Python implementation of the Subsonic server API.
|
||||||
|
|
||||||
|
Current supported features are:
|
||||||
|
|
||||||
|
* browsing (by folders or tags)
|
||||||
|
* streaming of various audio file formats
|
||||||
|
* transcoding
|
||||||
|
* user or random playlists
|
||||||
|
* cover arts (cover.jpg files in the same folder as music files)
|
||||||
|
* starred tracks/albums and ratings
|
||||||
|
* Last.FM scrobbling
|
||||||
|
""",
|
||||||
|
packages=['supysonic', 'supysonic.api', 'supysonic.frontend',
|
||||||
|
'supysonic.managers'],
|
||||||
|
scripts=['bin/supysonic-cli'],
|
||||||
|
package_data={'supysonic': ['templates/*.html']}
|
||||||
|
)
|
@ -20,7 +20,7 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from wsgiref.handlers import CGIHandler
|
from wsgiref.handlers import CGIHandler
|
||||||
from web import create_application
|
from supysonic.web import create_application
|
||||||
|
|
||||||
app = create_application()
|
app = create_application()
|
||||||
if app:
|
if app:
|
||||||
|
@ -20,7 +20,7 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from flup.server.fcgi import WSGIServer
|
from flup.server.fcgi import WSGIServer
|
||||||
from web import create_application
|
from supysonic.web import create_application
|
||||||
|
|
||||||
app = create_application()
|
app = create_application()
|
||||||
if app:
|
if app:
|
||||||
|
@ -21,6 +21,6 @@
|
|||||||
import sys
|
import sys
|
||||||
sys.path.insert(0, '/path/to/the/supysonic/app')
|
sys.path.insert(0, '/path/to/the/supysonic/app')
|
||||||
|
|
||||||
from web import create_application
|
from supysonic.web import create_application
|
||||||
application = create_application()
|
application = create_application()
|
||||||
|
|
||||||
|
0
supysonic/__init__.py
Normal file
0
supysonic/__init__.py
Normal file
@ -23,8 +23,8 @@ from xml.etree import ElementTree
|
|||||||
import simplejson
|
import simplejson
|
||||||
import uuid
|
import uuid
|
||||||
|
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from managers.user import UserManager
|
from supysonic.managers.user import UserManager
|
||||||
|
|
||||||
@app.before_request
|
@app.before_request
|
||||||
def set_formatter():
|
def set_formatter():
|
@ -24,8 +24,8 @@ from sqlalchemy.orm import aliased
|
|||||||
import random
|
import random
|
||||||
import uuid
|
import uuid
|
||||||
|
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import *
|
from supysonic.db import *
|
||||||
|
|
||||||
@app.route('/rest/getRandomSongs.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/getRandomSongs.view', methods = [ 'GET', 'POST' ])
|
||||||
def rand_songs():
|
def rand_songs():
|
@ -21,10 +21,10 @@
|
|||||||
import time
|
import time
|
||||||
import uuid
|
import uuid
|
||||||
from flask import request
|
from flask import request
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from . import get_entity
|
from . import get_entity
|
||||||
from lastfm import LastFm
|
from supysonic.lastfm import LastFm
|
||||||
from db import *
|
from supysonic.db import *
|
||||||
|
|
||||||
@app.route('/rest/star.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/star.view', methods = [ 'GET', 'POST' ])
|
||||||
def star():
|
def star():
|
@ -19,10 +19,10 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from flask import request
|
from flask import request
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import Folder, Artist, Album, Track
|
from supysonic.db import Folder, Artist, Album, Track
|
||||||
from . import get_entity
|
from . import get_entity
|
||||||
import uuid, time, string
|
import uuid, string
|
||||||
|
|
||||||
@app.route('/rest/getMusicFolders.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/getMusicFolders.view', methods = [ 'GET', 'POST' ])
|
||||||
def list_folders():
|
def list_folders():
|
@ -19,8 +19,8 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from flask import request
|
from flask import request
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import ChatMessage, session
|
from supysonic.db import ChatMessage, session
|
||||||
|
|
||||||
@app.route('/rest/getChatMessages.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/getChatMessages.view', methods = [ 'GET', 'POST' ])
|
||||||
def get_chat():
|
def get_chat():
|
@ -26,9 +26,9 @@ import subprocess
|
|||||||
import codecs
|
import codecs
|
||||||
from xml.etree import ElementTree
|
from xml.etree import ElementTree
|
||||||
|
|
||||||
import config, scanner
|
from supysonic import config, scanner
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import Track, Album, Artist, Folder, User, ClientPrefs, now, session
|
from supysonic.db import Track, Album, Artist, Folder, ClientPrefs, now, session
|
||||||
from . import get_entity
|
from . import get_entity
|
||||||
|
|
||||||
from sqlalchemy import func
|
from sqlalchemy import func
|
@ -21,8 +21,8 @@
|
|||||||
from flask import request
|
from flask import request
|
||||||
from sqlalchemy import or_, func
|
from sqlalchemy import or_, func
|
||||||
import uuid
|
import uuid
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import Playlist, User, Track, session
|
from supysonic.db import Playlist, User, Track, session
|
||||||
from . import get_entity
|
from . import get_entity
|
||||||
|
|
||||||
@app.route('/rest/getPlaylists.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/getPlaylists.view', methods = [ 'GET', 'POST' ])
|
@ -19,8 +19,8 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from flask import request
|
from flask import request
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import Folder, Track, Artist, Album
|
from supysonic.db import Folder, Track, Artist, Album
|
||||||
|
|
||||||
@app.route('/rest/search.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/search.view', methods = [ 'GET', 'POST' ])
|
||||||
def old_search():
|
def old_search():
|
@ -19,7 +19,7 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from flask import request
|
from flask import request
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
|
|
||||||
@app.route('/rest/ping.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/ping.view', methods = [ 'GET', 'POST' ])
|
||||||
def ping():
|
def ping():
|
@ -19,9 +19,9 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from flask import request
|
from flask import request
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import User
|
from supysonic.db import User
|
||||||
from managers.user import UserManager
|
from supysonic.managers.user import UserManager
|
||||||
|
|
||||||
@app.route('/rest/getUser.view', methods = [ 'GET', 'POST' ])
|
@app.route('/rest/getUser.view', methods = [ 'GET', 'POST' ])
|
||||||
def user_info():
|
def user_info():
|
@ -18,7 +18,7 @@
|
|||||||
# You should have received a copy of the GNU Affero General Public License
|
# You should have received a copy of the GNU Affero General Public License
|
||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
import config
|
from supysonic import config
|
||||||
|
|
||||||
from sqlalchemy import create_engine, Table, Column, ForeignKey, func
|
from sqlalchemy import create_engine, Table, Column, ForeignKey, func
|
||||||
from sqlalchemy import Integer, String, Boolean, DateTime
|
from sqlalchemy import Integer, String, Boolean, DateTime
|
||||||
@ -75,6 +75,7 @@ class UUID(TypeDecorator):
|
|||||||
def now():
|
def now():
|
||||||
return datetime.datetime.now().replace(microsecond = 0)
|
return datetime.datetime.now().replace(microsecond = 0)
|
||||||
|
|
||||||
|
config.check()
|
||||||
engine = create_engine(config.get('base', 'database_uri'), convert_unicode = True)
|
engine = create_engine(config.get('base', 'database_uri'), convert_unicode = True)
|
||||||
session = scoped_session(sessionmaker(autocommit = False, autoflush = False, bind = engine))
|
session = scoped_session(sessionmaker(autocommit = False, autoflush = False, bind = engine))
|
||||||
|
|
@ -18,8 +18,8 @@
|
|||||||
# You should have received a copy of the GNU Affero General Public License
|
# You should have received a copy of the GNU Affero General Public License
|
||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from managers.user import UserManager
|
from supysonic.managers.user import UserManager
|
||||||
|
|
||||||
app.add_template_filter(str)
|
app.add_template_filter(str)
|
||||||
|
|
@ -19,14 +19,13 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
from flask import request, flash, render_template, redirect, url_for, session as fl_sess
|
from flask import request, flash, render_template, redirect, url_for, session as fl_sess
|
||||||
import os.path
|
|
||||||
import uuid
|
import uuid
|
||||||
|
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from db import session, Folder
|
from supysonic.db import session, Folder
|
||||||
from scanner import Scanner
|
from supysonic.scanner import Scanner
|
||||||
from managers.user import UserManager
|
from supysonic.managers.user import UserManager
|
||||||
from managers.folder import FolderManager
|
from supysonic.managers.folder import FolderManager
|
||||||
|
|
||||||
@app.before_request
|
@app.before_request
|
||||||
def check_admin():
|
def check_admin():
|
@ -20,8 +20,8 @@
|
|||||||
|
|
||||||
from flask import request, session, flash, render_template, redirect, url_for
|
from flask import request, session, flash, render_template, redirect, url_for
|
||||||
import uuid
|
import uuid
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
import db
|
from supysonic import db
|
||||||
|
|
||||||
@app.route('/playlist')
|
@app.route('/playlist')
|
||||||
def playlist_index():
|
def playlist_index():
|
@ -20,12 +20,12 @@
|
|||||||
|
|
||||||
from flask import request, session, flash, render_template, redirect, url_for, make_response
|
from flask import request, session, flash, render_template, redirect, url_for, make_response
|
||||||
|
|
||||||
from web import app
|
from supysonic.web import app
|
||||||
from managers.user import UserManager
|
from supysonic.managers.user import UserManager
|
||||||
from db import User, ClientPrefs, session as db_sess
|
from supysonic.db import User, ClientPrefs, session as db_sess
|
||||||
import uuid, csv
|
import uuid, csv
|
||||||
import config
|
from supysonic import config
|
||||||
from lastfm import LastFm
|
from supysonic.lastfm import LastFm
|
||||||
|
|
||||||
@app.before_request
|
@app.before_request
|
||||||
def check_admin():
|
def check_admin():
|
@ -19,8 +19,8 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
import requests, hashlib
|
import requests, hashlib
|
||||||
import config
|
from supysonic import config
|
||||||
from db import session
|
from supysonic.db import session
|
||||||
|
|
||||||
class LastFm:
|
class LastFm:
|
||||||
def __init__(self, user, logger):
|
def __init__(self, user, logger):
|
@ -19,7 +19,7 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
import os.path, uuid
|
import os.path, uuid
|
||||||
from db import Folder, Artist, session
|
from supysonic.db import Folder, Artist, session
|
||||||
|
|
||||||
class FolderManager:
|
class FolderManager:
|
||||||
SUCCESS = 0
|
SUCCESS = 0
|
@ -21,7 +21,7 @@
|
|||||||
import string, random, hashlib
|
import string, random, hashlib
|
||||||
import uuid
|
import uuid
|
||||||
|
|
||||||
from db import User, session
|
from supysonic.db import User, session
|
||||||
|
|
||||||
class UserManager:
|
class UserManager:
|
||||||
SUCCESS = 0
|
SUCCESS = 0
|
@ -21,7 +21,7 @@
|
|||||||
import os, os.path
|
import os, os.path
|
||||||
import time, mimetypes
|
import time, mimetypes
|
||||||
import mutagen
|
import mutagen
|
||||||
import config, db
|
from supysonic import config, db
|
||||||
|
|
||||||
def get_mime(ext):
|
def get_mime(ext):
|
||||||
return mimetypes.guess_type('dummy.' + ext, False)[0] or config.get('mimetypes', ext) or 'application/octet-stream'
|
return mimetypes.guess_type('dummy.' + ext, False)[0] or config.get('mimetypes', ext) or 'application/octet-stream'
|
@ -19,9 +19,9 @@
|
|||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
import os.path
|
import os.path
|
||||||
from flask import Flask, request, session, flash, render_template, redirect, url_for
|
from flask import Flask
|
||||||
|
|
||||||
import config
|
from supysonic import config
|
||||||
|
|
||||||
def teardown(exception):
|
def teardown(exception):
|
||||||
db.session.remove()
|
db.session.remove()
|
||||||
@ -35,7 +35,7 @@ def create_application():
|
|||||||
if not os.path.exists(config.get('base', 'cache_dir')):
|
if not os.path.exists(config.get('base', 'cache_dir')):
|
||||||
os.makedirs(config.get('base', 'cache_dir'))
|
os.makedirs(config.get('base', 'cache_dir'))
|
||||||
|
|
||||||
import db
|
from supysonic import db
|
||||||
db.init_db()
|
db.init_db()
|
||||||
|
|
||||||
app = Flask(__name__)
|
app = Flask(__name__)
|
||||||
@ -50,8 +50,8 @@ def create_application():
|
|||||||
|
|
||||||
app.teardown_request(teardown)
|
app.teardown_request(teardown)
|
||||||
|
|
||||||
import frontend
|
from supysonic import frontend
|
||||||
import api
|
from supysonic import api
|
||||||
|
|
||||||
return app
|
return app
|
||||||
|
|
Loading…
Reference in New Issue
Block a user