This repository has been archived on 2023-02-28. You can view files and clone it, but cannot push or open issues or pull requests.
Files
blender-asset-manager/tests/test_cli.py

273 lines
7.3 KiB
Python
Raw Normal View History

2014-11-14 12:16:13 +01:00
#!/usr/bin/env python3
# Apache License, Version 2.0
"""
Test bam command line client
"""
# ------------------
# Ensure module path
import os
import sys
path = os.path.normpath(os.path.join(os.path.dirname(os.path.abspath(__file__)), "..", "client", "cli"))
if path not in sys.path:
sys.path.append(path)
del os, sys, path
# --------
# ------------------
# Ensure module path
import os
import sys
path = os.path.normpath(os.path.join(os.path.dirname(os.path.abspath(__file__)), "..", "webservice", "bam"))
if path not in sys.path:
sys.path.append(path)
del os, sys, path
# --------
import os
import sys
import shutil
import json
2014-11-14 17:01:40 +01:00
TEMP = "/tmp/bam_test"
# Separate tmp folder for server, since we don't reset the server at every test
TEMP_SERVER = "/tmp/bam_test_server"
2014-11-14 12:16:13 +01:00
PORT = 5555
2014-11-14 17:01:40 +01:00
PROJECT_NAME = "test_project"
2014-11-14 12:16:13 +01:00
def run(cmd, cwd=None):
# print(">>> ", " ".join(cmd))
import subprocess
kwargs = dict(
stderr=subprocess.PIPE,
stdout=subprocess.PIPE,
)
if cwd is not None:
kwargs["cwd"] = cwd
proc = subprocess.Popen(cmd, **kwargs)
stderr, stdout = proc.communicate()
return stdout
class CHDir:
__slots__ = (
"dir_old",
"dir_new",
)
def __init__(self, directory):
self.dir_old = os.getcwd()
self.dir_new = directory
def __enter__(self):
os.chdir(self.dir_new)
def __exit__(self, exc_type, exc_value, traceback):
os.chdir(self.dir_old)
class StdIO:
__slots__ = (
"stdout",
"stderr",
)
def __init__(self):
self.stdout = sys.stdout
self.stderr = sys.stderr
def read(self):
sys.stdout.seek(0)
sys.stderr.seek(0)
return sys.stdout.read(), sys.stderr.read()
def __enter__(self):
import io
sys.stdout = io.StringIO()
sys.stderr = io.StringIO()
return self
def __exit__(self, exc_type, exc_value, traceback):
sys.stdout = self.stdout
sys.stderr = self.stderr
def svn_repo_create(id_, dirname):
run(["svnadmin", "create", id_], cwd=dirname)
2014-11-14 17:01:40 +01:00
def svn_repo_checkout(path, dirname):
run(["svnadmin", "checkout", path, dirname])
2014-11-14 12:16:13 +01:00
def bam_run(argv, cwd=None):
with CHDir(cwd):
import bam
with StdIO() as fakeio:
bam.main(argv)
ret = fakeio.read()
return ret
#if __name__ == "__main__":
# main()
# ------------------------------------------------------------------------------
# Server
2014-11-14 17:01:40 +01:00
def server(mode='testing', debug=False):
"""Start development server via Flask app.run() in a separate thread. We need server
to run in order to check most of the client commands.
"""
2014-11-14 12:16:13 +01:00
import threading
2014-11-14 17:01:40 +01:00
def run_testing_server():
2014-11-14 12:16:13 +01:00
from application import app
# If we run the server in testing mode (the default) we override sqlite database,
2014-11-14 17:01:40 +01:00
# with a testing, disposable one (create TMP dir)
if mode == 'testing':
from application import db
from application.modules.projects.model import Project, ProjectSetting
# Override sqlite database
if not os.path.isdir(TEMP_SERVER):
os.makedirs(TEMP_SERVER)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///' + TEMP_SERVER + '/bam_test.db'
# Use the model definitions to create all the tables
db.create_all()
# Create a testing project, based on the global configuration (depends on a
# correct initialization of the SVN repo and on the creation of a checkout)
# TODO(fsiddi): turn these values in variables
project = Project(
name=PROJECT_NAME,
repository_path="/tmp/bam_test/remote_store/svn_checkout",
upload_path="/tmp/bam_test/remote_store/upload",
status="active"
)
db.session.add(project)
db.session.commit()
# Run the app in production mode (prevents tests to run twice)
app.run(port=PORT, debug=debug)
2014-11-14 12:16:13 +01:00
from multiprocessing import Process
2014-11-14 17:01:40 +01:00
p = Process(target=run_testing_server, args=())
2014-11-14 12:16:13 +01:00
p.start()
os.system("sleep 1")
return p
# ------------------------------------------------------------------------------
# Unit Tests
import unittest
class BamSessionTestCase(unittest.TestCase):
def setUp(self):
if not os.path.isdir(TEMP):
os.makedirs(TEMP)
2014-11-14 17:01:40 +01:00
# Create local storage folder
if not os.path.isdir(self.path_local_store):
os.makedirs(self.path_local_store)
# Create remote storage (usually is on the server).
2014-11-14 17:01:40 +01:00
# SVN repo and SVN checkout will live here
if not os.path.isdir(self.path_remote_store):
os.makedirs(self.path_remote_store)
# Check for SVN repo folder
path_svn_repo = os.path.join(self.path_remote_store, "svn_repo")
if not os.path.isdir(path_svn_repo):
os.makedirs(path_svn_repo)
2014-11-14 12:16:13 +01:00
2014-11-14 17:01:40 +01:00
# Create a fresh SVN repository
svn_repo_create(self.proj_name, path_svn_repo)
2014-11-14 12:16:13 +01:00
2014-11-14 17:01:40 +01:00
# Check for SVN checkout
path_svn_checkout = os.path.join(self.path_remote_store, "svn_checkout")
if not os.path.isdir(path_svn_checkout):
os.makedirs(path_svn_checkout)
2014-11-14 12:16:13 +01:00
2014-11-14 17:01:40 +01:00
# Create an SVN checkout of the freshly created repo
svn_repo_checkout(path_svn_checkout, self.proj_name)
2014-11-14 12:16:13 +01:00
def tearDown(self):
shutil.rmtree(TEMP)
def get_url(self):
url_full = "%s@%s/%s" % (self.user_name, self.server_addr, self.proj_name)
user_name, url = url_full.rpartition('@')[0::2]
return url_full, user_name, url
def init_defaults(self):
2014-11-14 17:01:40 +01:00
self.path_local_store = os.path.join(TEMP, "local_store")
self.path_remote_store = os.path.join(TEMP, "remote_store")
2014-11-14 12:16:13 +01:00
2014-11-14 17:01:40 +01:00
self.proj_name = PROJECT_NAME
2014-11-14 12:16:13 +01:00
self.user_name = "user"
self.server_addr = "http://localhost:%s" % PORT
def init_repo(self):
url_full, user_name, url = self.get_url()
2014-11-14 17:01:40 +01:00
bam_run(["init", url_full], self.path_local_store)
2014-11-14 12:16:13 +01:00
class BamInitTest(BamSessionTestCase):
2014-11-14 12:28:05 +01:00
"""Test the `bam init user@http://bamserver/projectname` command.
We verify that a project folder is created, and that it contains a .bam subfolder
with a config file, with the right url and user values (given in the command)
"""
2014-11-14 12:16:13 +01:00
def __init__(self, *args):
self.init_defaults()
super().__init__(*args)
def test_init(self):
self.init_repo()
url_full, user_name, url = self.get_url()
2014-11-14 17:01:40 +01:00
with open(os.path.join(self.path_local_store, self.proj_name, ".bam", "config")) as f:
2014-11-14 12:16:13 +01:00
cfg = json.load(f)
self.assertEqual(url, cfg["url"])
self.assertEqual(user_name, cfg["user"])
class BamListTest(BamSessionTestCase):
2014-11-14 12:28:05 +01:00
"""Test for the `bam ls --json` command. We run it with --json for easier command
output parsing.
2014-11-14 12:28:05 +01:00
"""
2014-11-14 12:16:13 +01:00
def __init__(self, *args):
self.init_defaults()
super().__init__(*args)
def test_ls(self):
self.init_repo()
2014-11-14 17:01:40 +01:00
d = os.path.join(self.path_local_store, self.proj_name)
2014-11-14 12:16:13 +01:00
stdout, stderr = bam_run(["ls", "--json"], d)
self.assertEqual("", stderr)
import json
ret = json.loads(stdout)
if __name__ == '__main__':
p = server()
unittest.main(exit=False)
p.terminate()
shutil.rmtree(TEMP_SERVER, ignore_errors=True)
2014-11-14 12:16:13 +01:00