mirror of
https://github.com/aptly-dev/aptly.git
synced 2026-06-16 07:10:54 +00:00
Imported Upstream version 1.0.1
This commit is contained in:
@@ -0,0 +1,13 @@
|
||||
"""
|
||||
Testing aptly REST API
|
||||
"""
|
||||
|
||||
from .repos import *
|
||||
from .files import *
|
||||
from .publish import *
|
||||
from .version import *
|
||||
from .graph import *
|
||||
from .snapshots import *
|
||||
from .packages import *
|
||||
from .unix_socket import *
|
||||
from .systemd_handover import *
|
||||
@@ -0,0 +1,99 @@
|
||||
from api_lib import APITest
|
||||
|
||||
|
||||
class FilesAPITestUpload(APITest):
|
||||
"""
|
||||
POST /files/:dir
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
d = self.random_name()
|
||||
resp = self.upload("/api/files/" + d, "pyspi_0.6.1-1.3.dsc")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [d + '/pyspi_0.6.1-1.3.dsc'])
|
||||
self.check_exists("upload/" + d + '/pyspi_0.6.1-1.3.dsc')
|
||||
|
||||
|
||||
class FilesAPITestUploadMulti(APITest):
|
||||
"""
|
||||
POST /files/:dir, GET /files/:dir multi files
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
d = self.random_name()
|
||||
|
||||
self.check_equal(self.get("/api/files/" + d).status_code, 404)
|
||||
|
||||
resp = self.upload("/api/files/" + d, "pyspi_0.6.1-1.3.dsc", "pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(sorted(resp.json()),
|
||||
[d + '/pyspi_0.6.1-1.3.diff.gz', d + '/pyspi_0.6.1-1.3.dsc', d + '/pyspi_0.6.1.orig.tar.gz'])
|
||||
self.check_exists("upload/" + d + '/pyspi_0.6.1-1.3.dsc')
|
||||
self.check_exists("upload/" + d + '/pyspi_0.6.1-1.3.diff.gz')
|
||||
self.check_exists("upload/" + d + '/pyspi_0.6.1.orig.tar.gz')
|
||||
|
||||
resp = self.get("/api/files/" + d)
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(sorted(resp.json()),
|
||||
['pyspi_0.6.1-1.3.diff.gz', 'pyspi_0.6.1-1.3.dsc', 'pyspi_0.6.1.orig.tar.gz'])
|
||||
|
||||
|
||||
class FilesAPITestList(APITest):
|
||||
"""
|
||||
GET /files/
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
d1, d2, d3 = self.random_name(), self.random_name(), self.random_name()
|
||||
|
||||
resp = self.get("/api/files")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [])
|
||||
|
||||
self.check_equal(self.upload("/api/files/" + d1, "pyspi_0.6.1-1.3.dsc").status_code, 200)
|
||||
self.check_equal(self.upload("/api/files/" + d2, "pyspi_0.6.1-1.3.dsc").status_code, 200)
|
||||
self.check_equal(self.upload("/api/files/" + d3, "pyspi_0.6.1-1.3.dsc").status_code, 200)
|
||||
|
||||
resp = self.get("/api/files")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(sorted(resp.json()), sorted([d1, d2, d3]))
|
||||
|
||||
|
||||
class FilesAPITestDelete(APITest):
|
||||
"""
|
||||
DELETE /files/:dir, DELETE /files/:dir/:name
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
d1, d2 = self.random_name(), self.random_name()
|
||||
|
||||
self.check_equal(self.get("/api/files").json(), [])
|
||||
self.check_equal(self.delete("/api/files/" + d1).status_code, 200)
|
||||
self.check_equal(self.delete("/api/files/" + d1 + "/" + "pyspi_0.6.1-1.3.dsc").status_code, 200)
|
||||
|
||||
self.check_equal(self.upload("/api/files/" + d1, "pyspi_0.6.1-1.3.dsc").status_code, 200)
|
||||
self.check_equal(self.upload("/api/files/" + d2, "pyspi_0.6.1-1.3.dsc").status_code, 200)
|
||||
|
||||
self.check_equal(self.delete("/api/files/" + d1).status_code, 200)
|
||||
self.check_equal(self.get("/api/files").json(), [d2])
|
||||
|
||||
self.check_equal(self.delete("/api/files/" + d2 + "/" + "no-such-file").status_code, 200)
|
||||
self.check_equal(self.get("/api/files/" + d2).json(), ["pyspi_0.6.1-1.3.dsc"])
|
||||
|
||||
self.check_equal(self.delete("/api/files/" + d2 + "/" + "pyspi_0.6.1-1.3.dsc").status_code, 200)
|
||||
self.check_equal(self.get("/api/files").json(), [d2])
|
||||
self.check_equal(self.get("/api/files/" + d2).json(), [])
|
||||
|
||||
|
||||
class FilesAPITestSecurity(APITest):
|
||||
"""
|
||||
delete & upload security
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
self.check_equal(self.delete("/api/files/.").status_code, 400)
|
||||
self.check_equal(self.delete("/api/files").status_code, 405)
|
||||
self.check_equal(self.delete("/api/files/").status_code, 404)
|
||||
self.check_equal(self.delete("/api/files/../.").status_code, 400)
|
||||
self.check_equal(self.delete("/api/files/./..").status_code, 400)
|
||||
self.check_equal(self.delete("/api/files/dir/..").status_code, 400)
|
||||
@@ -0,0 +1,47 @@
|
||||
from api_lib import APITest
|
||||
import xml.etree.ElementTree as ET
|
||||
|
||||
|
||||
class GraphAPITest(APITest):
|
||||
"""
|
||||
GET /graph.:ext
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
resp = self.get("/api/graph.png")
|
||||
self.check_equal(resp.headers["Content-Type"], "image/png")
|
||||
self.check_equal(resp.content[:4], '\x89PNG')
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": "xyz", "Comment": "fun repo"}).status_code, 201)
|
||||
resp = self.get("/api/graph.svg")
|
||||
self.check_equal(resp.headers["Content-Type"], "image/svg+xml")
|
||||
self.check_equal(resp.content[:4], '<?xm')
|
||||
|
||||
resp = self.get("/api/graph.dot")
|
||||
self.check_equal(resp.headers["Content-Type"], "text/plain; charset=utf-8")
|
||||
self.check_equal(resp.content[:13], 'digraph aptly')
|
||||
|
||||
# basic test of layout:
|
||||
# horizontal should be wider than vertical
|
||||
# vertical should be higher than horizontal
|
||||
# for this to work we need at couple of repos
|
||||
tempRepos = [self.random_name() for r in range(3)]
|
||||
for repo in tempRepos:
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo, "Comment": "graph test repo"}).status_code, 201)
|
||||
|
||||
horizontal = self.get("/api/graph.svg?layout=horizontal").content
|
||||
vertical = self.get("/api/graph.svg?layout=vertical").content
|
||||
horizontalWidth = int(ET.fromstring(horizontal).get('width').replace("pt",""))
|
||||
horizontalHeight = int(ET.fromstring(horizontal).get('height').replace("pt",""))
|
||||
verticalWidth = int(ET.fromstring(vertical).get('width').replace("pt",""))
|
||||
verticalHeight = int(ET.fromstring(vertical).get('height').replace("pt",""))
|
||||
|
||||
self.check_gt(horizontalWidth, verticalWidth)
|
||||
self.check_gt(verticalHeight, horizontalHeight)
|
||||
|
||||
# make sure our default layout is horizontal
|
||||
self.check_equal(horizontal, self.get("/api/graph.svg").content)
|
||||
|
||||
# remove the repos again
|
||||
for repo in tempRepos:
|
||||
self.check_equal(self.delete("/api/repos/" + repo, params={"force": "1"}).status_code, 200)
|
||||
@@ -0,0 +1,44 @@
|
||||
import urllib
|
||||
from api_lib import APITest
|
||||
|
||||
|
||||
class PackagesAPITestShow(APITest):
|
||||
"""
|
||||
GET /api/packages/:key
|
||||
"""
|
||||
def check(self):
|
||||
# upload package to repo to create it
|
||||
repo_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"pyspi_0.6.1-1.3.dsc", "pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz").status_code, 200)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + "/file/" + d)
|
||||
self.check_equal(resp.status_code, 200)
|
||||
|
||||
# get information about package
|
||||
resp = self.get("/api/packages/" + urllib.quote('Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e'))
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), {
|
||||
'Architecture': 'any',
|
||||
'Binary': 'python-at-spi',
|
||||
'Build-Depends': 'debhelper (>= 5), cdbs, libatspi-dev, python-pyrex, python-support (>= 0.4), python-all-dev, libx11-dev',
|
||||
'Checksums-Sha1': ' 95a2468e4bbce730ba286f2211fa41861b9f1d90 3456 pyspi_0.6.1-1.3.diff.gz\n 56c8a9b1f4ab636052be8966690998cbe865cd6c 1782 pyspi_0.6.1-1.3.dsc\n 9694b80acc171c0a5bc99f707933864edfce555e 29063 pyspi_0.6.1.orig.tar.gz\n',
|
||||
'Checksums-Sha256': ' 2e770b28df948f3197ed0b679bdea99f3f2bf745e9ddb440c677df9c3aeaee3c 3456 pyspi_0.6.1-1.3.diff.gz\n d494aaf526f1ec6b02f14c2f81e060a5722d6532ddc760ec16972e45c2625989 1782 pyspi_0.6.1-1.3.dsc\n 64069ee828c50b1c597d10a3fefbba279f093a4723965388cdd0ac02f029bfb9 29063 pyspi_0.6.1.orig.tar.gz\n',
|
||||
'Checksums-Sha512': ' fde06b7dc5762a04986d0669420822f6a1e82b195322ae9cbd2dae40bda557c57ad77fe3546007ea645f801c4cd30ef4eb0e96efb2dee6b71c4c9a187d643683 1782 pyspi_0.6.1-1.3.dsc\n',
|
||||
'Files': ' 22ff26db69b73d3438fdde21ab5ba2f1 3456 pyspi_0.6.1-1.3.diff.gz\n b72cb94699298a117b7c82641c68b6fd 1782 pyspi_0.6.1-1.3.dsc\n def336bd566ea688a06ec03db7ccf1f4 29063 pyspi_0.6.1.orig.tar.gz\n',
|
||||
'FilesHash': '3a8b37cbd9a3559e',
|
||||
'Format': '1.0',
|
||||
'Homepage': 'http://people.redhat.com/zcerza/dogtail',
|
||||
'Key': 'Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e',
|
||||
'Maintainer': 'Jose Carlos Garcia Sogo <jsogo@debian.org>',
|
||||
'Package': 'pyspi',
|
||||
'ShortKey': 'Psource pyspi 0.6.1-1.3',
|
||||
'Standards-Version': '3.7.3',
|
||||
'Vcs-Svn': 'svn://svn.tribulaciones.org/srv/svn/pyspi/trunk',
|
||||
'Version': '0.6.1-1.3'})
|
||||
|
||||
resp = self.get("/api/packages/" + urllib.quote('Pamd64 no-such-package 1.0 3a8b37cbd9a3559e'))
|
||||
self.check_equal(resp.status_code, 404)
|
||||
@@ -0,0 +1,289 @@
|
||||
import os
|
||||
import inspect
|
||||
|
||||
from api_lib import APITest
|
||||
|
||||
DefaultSigningOptions = {
|
||||
"Keyring": os.path.join(os.path.dirname(inspect.getsourcefile(APITest)), "files") + "/aptly.pub",
|
||||
"SecretKeyring": os.path.join(os.path.dirname(inspect.getsourcefile(APITest)), "files") + "/aptly.sec",
|
||||
}
|
||||
|
||||
|
||||
class PublishAPITestRepo(APITest):
|
||||
"""
|
||||
POST /publish/:prefix (local repos), GET /publish
|
||||
"""
|
||||
fixtureGpg = True
|
||||
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "DefaultDistribution": "wheezy"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb", "pyspi_0.6.1-1.3.dsc",
|
||||
"pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz",
|
||||
"pyspi-0.6.1-1.3.stripped.dsc").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
# publishing under prefix, default distribution
|
||||
prefix = self.random_name()
|
||||
resp = self.post("/api/publish/" + prefix,
|
||||
json={
|
||||
"SourceKind": "local",
|
||||
"Sources": [{"Name": repo_name}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
})
|
||||
repo_expected = {
|
||||
'Architectures': ['i386', 'source'],
|
||||
'Distribution': 'wheezy',
|
||||
'Label': '',
|
||||
'Origin': '',
|
||||
'Prefix': prefix,
|
||||
'SkipContents': False,
|
||||
'SourceKind': 'local',
|
||||
'Sources': [{'Component': 'main', 'Name': repo_name}],
|
||||
'Storage': ''}
|
||||
|
||||
self.check_equal(resp.status_code, 201)
|
||||
self.check_equal(resp.json(), repo_expected)
|
||||
|
||||
all_repos = self.get("/api/publish")
|
||||
self.check_equal(all_repos.status_code, 200)
|
||||
self.check_in(repo_expected, all_repos.json())
|
||||
|
||||
self.check_exists("public/" + prefix + "/dists/wheezy/Release")
|
||||
self.check_exists("public/" + prefix + "/dists/wheezy/main/binary-i386/Packages")
|
||||
self.check_exists("public/" + prefix + "/dists/wheezy/main/Contents-i386.gz")
|
||||
self.check_exists("public/" + prefix + "/dists/wheezy/main/source/Sources")
|
||||
self.check_exists("public/" + prefix + "/pool/main/b/boost-defaults/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
|
||||
# publishing under root, custom distribution, architectures
|
||||
distribution = self.random_name()
|
||||
resp = self.post("/api/publish/:.",
|
||||
json={
|
||||
"SourceKind": "local",
|
||||
"Sources": [{"Name": repo_name}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
"Distribution": distribution,
|
||||
"Architectures": ["i386", "amd64"],
|
||||
})
|
||||
repo2_expected = {
|
||||
'Architectures': ['amd64', 'i386'],
|
||||
'Distribution': distribution,
|
||||
'Label': '',
|
||||
'Origin': '',
|
||||
'Prefix': ".",
|
||||
'SkipContents': False,
|
||||
'SourceKind': 'local',
|
||||
'Sources': [{'Component': 'main', 'Name': repo_name}],
|
||||
'Storage': ''}
|
||||
self.check_equal(resp.status_code, 201)
|
||||
self.check_equal(resp.json(), repo2_expected)
|
||||
|
||||
self.check_exists("public/dists/" + distribution + "/Release")
|
||||
self.check_exists("public/dists/" + distribution + "/main/binary-i386/Packages")
|
||||
self.check_exists("public/dists/" + distribution + "/main/Contents-i386.gz")
|
||||
self.check_exists("public/dists/" + distribution + "/main/binary-amd64/Packages")
|
||||
self.check_not_exists("public/dists/" + distribution + "/main/Contents-amd64.gz")
|
||||
self.check_exists("public/pool/main/b/boost-defaults/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
|
||||
all_repos = self.get("/api/publish")
|
||||
self.check_equal(all_repos.status_code, 200)
|
||||
self.check_in(repo_expected, all_repos.json())
|
||||
self.check_in(repo2_expected, all_repos.json())
|
||||
|
||||
|
||||
class PublishSnapshotAPITest(APITest):
|
||||
"""
|
||||
POST /publish/:prefix (snapshots), GET /publish
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
snapshot_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name}).status_code, 201)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot_name})
|
||||
self.check_equal(resp.status_code, 400)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot_name}).status_code, 201)
|
||||
|
||||
prefix = self.random_name()
|
||||
resp = self.post("/api/publish/" + prefix,
|
||||
json={
|
||||
"SourceKind": "snapshot",
|
||||
"Sources": [{"Name": snapshot_name}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
"Distribution": "squeeze",
|
||||
})
|
||||
self.check_equal(resp.status_code, 201)
|
||||
self.check_equal(resp.json(), {
|
||||
'Architectures': ['i386'],
|
||||
'Distribution': 'squeeze',
|
||||
'Label': '',
|
||||
'Origin': '',
|
||||
'Prefix': prefix,
|
||||
'SkipContents': False,
|
||||
'SourceKind': 'snapshot',
|
||||
'Sources': [{'Component': 'main', 'Name': snapshot_name}],
|
||||
'Storage': ''})
|
||||
|
||||
self.check_exists("public/" + prefix + "/dists/squeeze/Release")
|
||||
self.check_exists("public/" + prefix + "/dists/squeeze/main/binary-i386/Packages")
|
||||
self.check_exists("public/" + prefix + "/dists/squeeze/main/Contents-i386.gz")
|
||||
self.check_exists("public/" + prefix + "/pool/main/b/boost-defaults/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
|
||||
|
||||
class PublishUpdateAPITestRepo(APITest):
|
||||
"""
|
||||
PUT /publish/:prefix/:distribution (local repos), DELETE /publish/:prefix/:distribution
|
||||
"""
|
||||
fixtureGpg = True
|
||||
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "DefaultDistribution": "wheezy"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"pyspi_0.6.1-1.3.dsc",
|
||||
"pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz",
|
||||
"pyspi-0.6.1-1.3.stripped.dsc").status_code, 200)
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
prefix = self.random_name()
|
||||
resp = self.post("/api/publish/" + prefix,
|
||||
json={
|
||||
"Architectures": ["i386", "source"],
|
||||
"SourceKind": "local",
|
||||
"Sources": [{"Name": repo_name}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
})
|
||||
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
self.check_not_exists("public/" + prefix + "/pool/main/b/boost-defaults/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
self.check_exists("public/" + prefix + "/pool/main/p/pyspi/pyspi-0.6.1-1.3.stripped.dsc")
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name + "/packages/",
|
||||
json={"PackageRefs": ['Psource pyspi 0.6.1-1.4 f8f1daa806004e89']}).status_code, 200)
|
||||
|
||||
resp = self.put("/api/publish/" + prefix + "/wheezy",
|
||||
json={
|
||||
"Signing": DefaultSigningOptions,
|
||||
})
|
||||
repo_expected = {
|
||||
'Architectures': ['i386', 'source'],
|
||||
'Distribution': 'wheezy',
|
||||
'Label': '',
|
||||
'Origin': '',
|
||||
'Prefix': prefix,
|
||||
'SkipContents': False,
|
||||
'SourceKind': 'local',
|
||||
'Sources': [{'Component': 'main', 'Name': repo_name}],
|
||||
'Storage': ''}
|
||||
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), repo_expected)
|
||||
|
||||
self.check_exists("public/" + prefix + "/pool/main/b/boost-defaults/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
self.check_not_exists("public/" + prefix + "/pool/main/p/pyspi/pyspi-0.6.1-1.3.stripped.dsc")
|
||||
|
||||
self.check_equal(self.delete("/api/publish/" + prefix + "/wheezy").status_code, 200)
|
||||
self.check_not_exists("public/" + prefix + "dists/")
|
||||
|
||||
|
||||
class PublishSwitchAPITestRepo(APITest):
|
||||
"""
|
||||
PUT /publish/:prefix/:distribution (snapshots), DELETE /publish/:prefix/:distribution
|
||||
"""
|
||||
fixtureGpg = True
|
||||
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "DefaultDistribution": "wheezy"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"pyspi_0.6.1-1.3.dsc",
|
||||
"pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz",
|
||||
"pyspi-0.6.1-1.3.stripped.dsc").status_code, 200)
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
snapshot1_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot1_name}).status_code, 201)
|
||||
|
||||
prefix = self.random_name()
|
||||
resp = self.post("/api/publish/" + prefix,
|
||||
json={
|
||||
"Architectures": ["i386", "source"],
|
||||
"SourceKind": "snapshot",
|
||||
"Sources": [{"Name": snapshot1_name}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
})
|
||||
|
||||
self.check_equal(resp.status_code, 201)
|
||||
repo_expected = {
|
||||
'Architectures': ['i386', 'source'],
|
||||
'Distribution': 'wheezy',
|
||||
'Label': '',
|
||||
'Origin': '',
|
||||
'Prefix': prefix,
|
||||
'SkipContents': False,
|
||||
'SourceKind': 'snapshot',
|
||||
'Sources': [{'Component': 'main', 'Name': snapshot1_name}],
|
||||
'Storage': ''}
|
||||
self.check_equal(resp.json(), repo_expected)
|
||||
|
||||
self.check_not_exists("public/" + prefix + "/pool/main/b/boost-defaults/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
self.check_exists("public/" + prefix + "/pool/main/p/pyspi/pyspi-0.6.1-1.3.stripped.dsc")
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name + "/packages/",
|
||||
json={"PackageRefs": ['Psource pyspi 0.6.1-1.4 f8f1daa806004e89']}).status_code, 200)
|
||||
|
||||
snapshot2_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot2_name}).status_code, 201)
|
||||
|
||||
resp = self.put("/api/publish/" + prefix + "/wheezy",
|
||||
json={
|
||||
"Snapshots": [{"Component": "main", "Name": snapshot2_name}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
"SkipContents": True,
|
||||
})
|
||||
repo_expected = {
|
||||
'Architectures': ['i386', 'source'],
|
||||
'Distribution': 'wheezy',
|
||||
'Label': '',
|
||||
'Origin': '',
|
||||
'Prefix': prefix,
|
||||
'SkipContents': True,
|
||||
'SourceKind': 'snapshot',
|
||||
'Sources': [{'Component': 'main', 'Name': snapshot2_name}],
|
||||
'Storage': ''}
|
||||
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), repo_expected)
|
||||
|
||||
self.check_exists("public/" + prefix + "/pool/main/b/boost-defaults/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
self.check_not_exists("public/" + prefix + "/pool/main/p/pyspi/pyspi-0.6.1-1.3.stripped.dsc")
|
||||
|
||||
self.check_equal(self.delete("/api/publish/" + prefix + "/wheezy").status_code, 200)
|
||||
self.check_not_exists("public/" + prefix + "dists/")
|
||||
@@ -0,0 +1,296 @@
|
||||
from api_lib import APITest
|
||||
from publish import DefaultSigningOptions
|
||||
|
||||
|
||||
class ReposAPITestCreateShow(APITest):
|
||||
"""
|
||||
GET /api/repos/:name, POST /api/repos, GET /api/repos/:name/packages
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
repo_desc = {u'Comment': u'fun repo',
|
||||
u'DefaultComponent': u'',
|
||||
u'DefaultDistribution': u'',
|
||||
u'Name': repo_name}
|
||||
|
||||
resp = self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"})
|
||||
self.check_equal(resp.json(), repo_desc)
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
self.check_equal(self.get("/api/repos/" + repo_name).json(), repo_desc)
|
||||
self.check_equal(self.get("/api/repos/" + repo_name).status_code, 200)
|
||||
|
||||
resp = self.get("/api/repos/" + repo_name + "/packages")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [])
|
||||
|
||||
self.check_equal(self.get("/api/repos/" + self.random_name()).status_code, 404)
|
||||
|
||||
|
||||
class ReposAPITestCreateIndexDelete(APITest):
|
||||
"""
|
||||
GET /api/repos, POST /api/repos, DELETE /api/repos/:name
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
repos = self.get("/api/repos/").json()
|
||||
names = [repo["Name"] for repo in repos]
|
||||
assert repo_name in names
|
||||
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name).status_code, 200)
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name).status_code, 404)
|
||||
|
||||
self.check_equal(self.get("/api/repos/" + repo_name).status_code, 404)
|
||||
|
||||
self.check_equal(self.delete("/api/repos/" + self.random_name()).status_code, 404)
|
||||
|
||||
# create once again
|
||||
distribution = self.random_name()
|
||||
self.check_equal(self.post("/api/repos",
|
||||
json={
|
||||
"Name": repo_name,
|
||||
"Comment": "fun repo",
|
||||
"DefaultDistribution": distribution
|
||||
}).status_code, 201)
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"pyspi_0.6.1-1.3.dsc", "pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz").status_code, 200)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + "/file/" + d)
|
||||
self.check_equal(resp.status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/snapshots", json={"Name": repo_name}).status_code, 201)
|
||||
|
||||
self.check_equal(self.post("/api/publish",
|
||||
json={
|
||||
"SourceKind": "local",
|
||||
"Sources": [{"Name": repo_name}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
}).status_code, 201)
|
||||
|
||||
# repo is not deletable while it is published
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name).status_code, 409)
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name, params={"force": "1"}).status_code, 409)
|
||||
|
||||
# drop published
|
||||
self.check_equal(self.delete("/api/publish//" + distribution).status_code, 200)
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name).status_code, 409)
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name, params={"force": "1"}).status_code, 200)
|
||||
self.check_equal(self.get("/api/repos/" + repo_name).status_code, 404)
|
||||
|
||||
|
||||
class ReposAPITestAdd(APITest):
|
||||
"""
|
||||
POST /api/repos/:name/file/:dir, GET /api/repos/:name/packages
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"pyspi_0.6.1-1.3.dsc", "pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz").status_code, 200)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + "/file/" + d)
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), {
|
||||
u'FailedFiles': [],
|
||||
u'Report': {
|
||||
u'Added': [u'pyspi_0.6.1-1.3_source added'],
|
||||
u'Removed': [],
|
||||
u'Warnings': []}})
|
||||
|
||||
self.check_equal(self.get("/api/repos/" + repo_name + "/packages").json(), ['Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e'])
|
||||
|
||||
self.check_not_exists("upload/" + d)
|
||||
|
||||
|
||||
class ReposAPITestAddNotFullRemove(APITest):
|
||||
"""
|
||||
POST /api/repos/:name/file/:dir not all files removed
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"pyspi_0.6.1-1.3.dsc", "pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz", "aptly.pub").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
self.check_equal(self.get("/api/repos/" + repo_name + "/packages").json(), ['Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e'])
|
||||
|
||||
self.check_exists("upload/" + d + "/aptly.pub")
|
||||
self.check_not_exists("upload/" + d + "/pyspi_0.6.1-1.3.dsc")
|
||||
|
||||
|
||||
class ReposAPITestAddNoRemove(APITest):
|
||||
"""
|
||||
POST /api/repos/:name/file/:dir no remove
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"pyspi_0.6.1-1.3.dsc", "pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d, params={"noRemove": 1}).status_code, 200)
|
||||
self.check_equal(self.get("/api/repos/" + repo_name + "/packages").json(), ['Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e'])
|
||||
|
||||
self.check_exists("upload/" + d + "/pyspi_0.6.1-1.3.dsc")
|
||||
|
||||
|
||||
class ReposAPITestAddFile(APITest):
|
||||
"""
|
||||
POST /api/repos/:name/file/:dir/:file
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + "/file/" + d + "/libboost-program-options-dev_1.49.0.1_i386.deb")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), {
|
||||
u'FailedFiles': [],
|
||||
u'Report': {
|
||||
u'Added': [u'libboost-program-options-dev_1.49.0.1_i386 added'],
|
||||
u'Removed': [],
|
||||
u'Warnings': []}})
|
||||
|
||||
self.check_equal(self.get("/api/repos/" + repo_name + "/packages").json(),
|
||||
['Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378'])
|
||||
|
||||
self.check_not_exists("upload/" + d)
|
||||
|
||||
|
||||
class ReposAPITestShowQuery(APITest):
|
||||
"""
|
||||
GET /api/repos/:name/packages?q=query
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb", "pyspi_0.6.1-1.3.dsc",
|
||||
"pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz",
|
||||
"pyspi-0.6.1-1.3.stripped.dsc").status_code, 200)
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages", params={"q": "pyspi"}).json()),
|
||||
['Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e', 'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages", params={"q": "Version (> 0.6.1-1.4)"}).json()),
|
||||
['Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378', 'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
|
||||
self.check_equal(sorted(p['Key'] for p in self.get("/api/repos/" + repo_name + "/packages",
|
||||
params={"q": "pyspi", "format": "details"}).json()),
|
||||
['Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e', 'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
|
||||
resp = self.get("/api/repos/" + repo_name + "/packages", params={"q": "pyspi)"})
|
||||
self.check_equal(resp.status_code, 400)
|
||||
self.check_equal(resp.json()[0]["error"], u'parsing failed: unexpected token ): expecting end of query')
|
||||
|
||||
|
||||
class ReposAPITestAddMultiple(APITest):
|
||||
"""
|
||||
POST /api/repos/:name/file/:dir/:file multiple
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb", "pyspi_0.6.1-1.3.dsc",
|
||||
"pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz",
|
||||
"pyspi-0.6.1-1.3.stripped.dsc").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d + "/pyspi_0.6.1-1.3.dsc",
|
||||
params={"noRemove": 1}).status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages").json()),
|
||||
['Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e'])
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d + "/pyspi-0.6.1-1.3.stripped.dsc").status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages").json()),
|
||||
['Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e', 'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
|
||||
|
||||
class ReposAPITestPackagesAddDelete(APITest):
|
||||
"""
|
||||
POST/DELETE /api/repos/:name/packages
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb", "pyspi_0.6.1-1.3.dsc",
|
||||
"pyspi_0.6.1-1.3.diff.gz", "pyspi_0.6.1.orig.tar.gz",
|
||||
"pyspi-0.6.1-1.3.stripped.dsc").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages").json()),
|
||||
['Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378',
|
||||
'Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e',
|
||||
'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/packages/",
|
||||
json={"PackageRefs": ['Psource pyspi 0.6.1-1.4 f8f1daa806004e89']}).status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages").json()),
|
||||
['Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378',
|
||||
'Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e',
|
||||
'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/packages/",
|
||||
json={"PackageRefs": ['Psource pyspi 0.6.1-1.4 f8f1daa806004e89',
|
||||
'Psource no-such-package 0.6.1-1.4 f8f1daa806004e89']}).status_code, 404)
|
||||
|
||||
self.check_equal(self.delete("/api/repos/" + repo_name + "/packages/",
|
||||
json={"PackageRefs": ['Psource pyspi 0.6.1-1.4 f8f1daa806004e89']}).status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages").json()),
|
||||
['Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378',
|
||||
'Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e'])
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/packages/",
|
||||
json={"PackageRefs": ['Psource pyspi 0.6.1-1.4 f8f1daa806004e89']}).status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name + "/packages").json()),
|
||||
['Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378',
|
||||
'Psource pyspi 0.6.1-1.3 3a8b37cbd9a3559e',
|
||||
'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
|
||||
repo_name2 = self.random_name()
|
||||
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name2, "Comment": "fun repo"}).status_code, 201)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name2 + "/packages/",
|
||||
json={"PackageRefs": ['Psource pyspi 0.6.1-1.4 f8f1daa806004e89',
|
||||
'Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378']}).status_code, 200)
|
||||
|
||||
self.check_equal(sorted(self.get("/api/repos/" + repo_name2 + "/packages").json()),
|
||||
['Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378',
|
||||
'Psource pyspi 0.6.1-1.4 f8f1daa806004e89'])
|
||||
@@ -0,0 +1,276 @@
|
||||
from api_lib import APITest
|
||||
from publish import DefaultSigningOptions
|
||||
|
||||
|
||||
class SnapshotsAPITestCreateShowEmpty(APITest):
|
||||
"""
|
||||
GET /api/snapshots/:name, POST /api/snapshots, GET /api/snapshots/:name/packages
|
||||
"""
|
||||
def check(self):
|
||||
snapshot_name = self.random_name()
|
||||
snapshot_desc = {u'Description': u'fun snapshot',
|
||||
u'Name': snapshot_name}
|
||||
|
||||
# create empty snapshot
|
||||
resp = self.post("/api/snapshots", json=snapshot_desc)
|
||||
self.check_subset(snapshot_desc, resp.json())
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
self.check_subset(snapshot_desc, self.get("/api/snapshots/" + snapshot_name).json())
|
||||
self.check_equal(self.get("/api/snapshots/" + snapshot_name).status_code, 200)
|
||||
|
||||
resp = self.get("/api/snapshots/" + snapshot_name + "/packages")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [])
|
||||
|
||||
self.check_equal(self.get("/api/snapshots/" + self.random_name()).status_code, 404)
|
||||
|
||||
# create snapshot with duplicate name
|
||||
resp = self.post("/api/snapshots", json=snapshot_desc)
|
||||
self.check_equal(resp.status_code, 400)
|
||||
|
||||
|
||||
class SnapshotsAPITestCreateFromRefs(APITest):
|
||||
"""
|
||||
GET /api/snapshots/:name, POST /api/snapshots, GET /api/snapshots/:name/packages,
|
||||
GET /api/snapshots
|
||||
"""
|
||||
def check(self):
|
||||
snapshot_name = self.random_name()
|
||||
snapshot_desc = {u'Description': u'fun snapshot',
|
||||
u'Name': snapshot_name,
|
||||
u'SourceSnapshots': [self.random_name()]}
|
||||
|
||||
# creating snapshot from missing source snapshot
|
||||
resp = self.post("/api/snapshots", json=snapshot_desc)
|
||||
self.check_equal(resp.status_code, 404)
|
||||
|
||||
# create empty snapshot
|
||||
empty_snapshot_name = self.random_name()
|
||||
resp = self.post("/api/snapshots", json={"Name": empty_snapshot_name})
|
||||
self.check_equal(resp.status_code, 201)
|
||||
self.check_equal(resp.json()['Description'], 'Created as empty')
|
||||
|
||||
# create and upload package to repo to register package in DB
|
||||
repo_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name}).status_code, 201)
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
# create snapshot with empty snapshot as source and package
|
||||
snapshot = snapshot_desc.copy()
|
||||
snapshot['PackageRefs'] = ["Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378"]
|
||||
snapshot['SourceSnapshots'] = [empty_snapshot_name]
|
||||
resp = self.post("/api/snapshots", json=snapshot)
|
||||
self.check_equal(resp.status_code, 201)
|
||||
snapshot.pop('SourceSnapshots')
|
||||
snapshot.pop('PackageRefs')
|
||||
self.check_subset(snapshot, resp.json())
|
||||
|
||||
self.check_subset(snapshot, self.get("/api/snapshots/" + snapshot_name).json())
|
||||
resp = self.get("/api/snapshots/" + snapshot_name + "/packages")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), ["Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378"])
|
||||
|
||||
# create snapshot with unreferenced package
|
||||
resp = self.post("/api/snapshots", json={
|
||||
"Name": self.random_name(),
|
||||
"PackageRefs": ["Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378", "Pamd64 no-such-package 1.2 91"]})
|
||||
self.check_equal(resp.status_code, 404)
|
||||
|
||||
# list snapshots
|
||||
resp = self.get("/api/snapshots", params={"sort": "time"})
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal([s["Name"] for s in resp.json() if s["Name"] in [empty_snapshot_name, snapshot_name]],
|
||||
[empty_snapshot_name, snapshot_name])
|
||||
|
||||
|
||||
class SnapshotsAPITestCreateFromRepo(APITest):
|
||||
"""
|
||||
POST /api/repos, POST /api/repos/:name/snapshots, GET /api/snapshots/:name
|
||||
"""
|
||||
def check(self):
|
||||
repo_name = self.random_name()
|
||||
snapshot_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name}).status_code, 201)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot_name})
|
||||
self.check_equal(resp.status_code, 400)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot_name})
|
||||
self.check_equal(resp.status_code, 201)
|
||||
self.check_equal(self.get("/api/snapshots/" + snapshot_name).status_code, 200)
|
||||
|
||||
self.check_subset({u'Architecture': 'i386',
|
||||
u'Package': 'libboost-program-options-dev',
|
||||
u'Version': '1.49.0.1',
|
||||
'FilesHash': '918d2f433384e378'},
|
||||
self.get("/api/snapshots/" + snapshot_name + "/packages", params={"format": "details"}).json()[0])
|
||||
|
||||
self.check_subset({u'Architecture': 'i386',
|
||||
u'Package': 'libboost-program-options-dev',
|
||||
u'Version': '1.49.0.1',
|
||||
'FilesHash': '918d2f433384e378'},
|
||||
self.get("/api/snapshots/" + snapshot_name + "/packages",
|
||||
params={"format": "details", "q": "Version (> 0.6.1-1.4)"}).json()[0])
|
||||
|
||||
# duplicate snapshot name
|
||||
resp = self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot_name})
|
||||
self.check_equal(resp.status_code, 400)
|
||||
|
||||
|
||||
class SnapshotsAPITestCreateUpdate(APITest):
|
||||
"""
|
||||
POST /api/snapshots, PUT /api/snapshots/:name, GET /api/snapshots/:name
|
||||
"""
|
||||
def check(self):
|
||||
snapshot_name = self.random_name()
|
||||
snapshot_desc = {u'Description': u'fun snapshot',
|
||||
u'Name': snapshot_name}
|
||||
|
||||
resp = self.post("/api/snapshots", json=snapshot_desc)
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
new_snapshot_name = self.random_name()
|
||||
resp = self.put("/api/snapshots/" + snapshot_name, json={'Name': new_snapshot_name,
|
||||
'Description': 'New description'})
|
||||
self.check_equal(resp.status_code, 200)
|
||||
|
||||
resp = self.get("/api/snapshots/" + new_snapshot_name)
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_subset({"Name": new_snapshot_name,
|
||||
"Description": "New description"}, resp.json())
|
||||
|
||||
# duplicate name
|
||||
resp = self.put("/api/snapshots/" + new_snapshot_name, json={'Name': new_snapshot_name,
|
||||
'Description': 'New description'})
|
||||
self.check_equal(resp.status_code, 409)
|
||||
|
||||
# missing snapshot
|
||||
resp = self.put("/api/snapshots/" + snapshot_name, json={})
|
||||
self.check_equal(resp.status_code, 404)
|
||||
|
||||
|
||||
class SnapshotsAPITestCreateDelete(APITest):
|
||||
"""
|
||||
POST /api/snapshots, DELETE /api/snapshots/:name, GET /api/snapshots/:name
|
||||
"""
|
||||
def check(self):
|
||||
snapshot_name = self.random_name()
|
||||
snapshot_desc = {u'Description': u'fun snapshot',
|
||||
u'Name': snapshot_name}
|
||||
|
||||
# deleting unreferenced snapshot
|
||||
resp = self.post("/api/snapshots", json=snapshot_desc)
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
self.check_equal(self.delete("/api/snapshots/" + snapshot_name).status_code, 200)
|
||||
|
||||
self.check_equal(self.get("/api/snapshots/" + snapshot_name).status_code, 404)
|
||||
|
||||
# deleting referenced snapshot
|
||||
snap1, snap2 = self.random_name(), self.random_name()
|
||||
self.check_equal(self.post("/api/snapshots", json={"Name": snap1}).status_code, 201)
|
||||
self.check_equal(self.post("/api/snapshots", json={"Name": snap2, "SourceSnapshots": [snap1]}).status_code, 201)
|
||||
|
||||
self.check_equal(self.delete("/api/snapshots/" + snap1).status_code, 409)
|
||||
self.check_equal(self.get("/api/snapshots/" + snap1).status_code, 200)
|
||||
self.check_equal(self.delete("/api/snapshots/" + snap1, params={"force": "1"}).status_code, 200)
|
||||
self.check_equal(self.get("/api/snapshots/" + snap1).status_code, 404)
|
||||
|
||||
# deleting published snapshot
|
||||
resp = self.post("/api/publish",
|
||||
json={
|
||||
"SourceKind": "snapshot",
|
||||
"Distribution": "trusty",
|
||||
"Architectures": ["i386"],
|
||||
"Sources": [{"Name": snap2}],
|
||||
"Signing": DefaultSigningOptions,
|
||||
})
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
self.check_equal(self.delete("/api/snapshots/" + snap2).status_code, 409)
|
||||
self.check_equal(self.delete("/api/snapshots/" + snap2, params={"force": "1"}).status_code, 409)
|
||||
|
||||
|
||||
class SnapshotsAPITestSearch(APITest):
|
||||
"""
|
||||
POST /api/snapshots, GET /api/snapshots?sort=name, GET /api/snapshots/:name
|
||||
"""
|
||||
def check(self):
|
||||
|
||||
repo_name = self.random_name()
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
snapshot_name = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshot_name})
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
resp = self.get("/api/snapshots/" + snapshot_name + "/packages",
|
||||
params={"q": "libboost-program-options-dev", "format": "details"})
|
||||
self.check_equal(resp.status_code, 200)
|
||||
|
||||
self.check_equal(len(resp.json()), 1)
|
||||
self.check_equal(resp.json()[0]["Package"], "libboost-program-options-dev")
|
||||
|
||||
resp = self.get("/api/snapshots/" + snapshot_name + "/packages")
|
||||
self.check_equal(resp.status_code, 200)
|
||||
|
||||
self.check_equal(len(resp.json()), 1)
|
||||
self.check_equal(resp.json(), ["Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378"])
|
||||
|
||||
|
||||
class SnapshotsAPITestDiff(APITest):
|
||||
"""
|
||||
GET /api/snapshot/:name/diff/:name2
|
||||
"""
|
||||
def check(self):
|
||||
repos = [self.random_name() for x in xrange(2)]
|
||||
snapshots = [self.random_name() for x in xrange(2)]
|
||||
|
||||
for repo_name in repos:
|
||||
self.check_equal(self.post("/api/repos", json={"Name": repo_name}).status_code, 201)
|
||||
|
||||
d = self.random_name()
|
||||
self.check_equal(self.upload("/api/files/" + d,
|
||||
"libboost-program-options-dev_1.49.0.1_i386.deb").status_code, 200)
|
||||
|
||||
self.check_equal(self.post("/api/repos/" + repo_name + "/file/" + d).status_code, 200)
|
||||
|
||||
resp = self.post("/api/repos/" + repo_name + '/snapshots', json={'Name': snapshots[0]})
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
resp = self.post("/api/snapshots", json={'Name': snapshots[1]})
|
||||
self.check_equal(resp.status_code, 201)
|
||||
|
||||
resp = self.get("/api/snapshots/" + snapshots[0] + "/diff/" + snapshots[1])
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [{'Left': 'Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378',
|
||||
'Right': None}])
|
||||
|
||||
resp = self.get("/api/snapshots/" + snapshots[1] + "/diff/" + snapshots[0])
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [{'Right': 'Pi386 libboost-program-options-dev 1.49.0.1 918d2f433384e378',
|
||||
'Left': None}])
|
||||
|
||||
resp = self.get("/api/snapshots/" + snapshots[0] + "/diff/" + snapshots[0])
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [])
|
||||
|
||||
resp = self.get("/api/snapshots/" + snapshots[1] + "/diff/" + snapshots[1])
|
||||
self.check_equal(resp.status_code, 200)
|
||||
self.check_equal(resp.json(), [])
|
||||
@@ -0,0 +1,46 @@
|
||||
import requests_unixsocket
|
||||
import urllib
|
||||
import os
|
||||
import os.path
|
||||
|
||||
from lib import BaseTest
|
||||
|
||||
|
||||
class SystemdAPIHandoverTest(BaseTest):
|
||||
aptly_server = None
|
||||
socket_path = "/tmp/_aptly_systemdapihandovertest.sock"
|
||||
|
||||
def prepare(self):
|
||||
# On Debian they use /lib on other systems /usr/lib.
|
||||
systemd_activate = "/usr/lib/systemd/systemd-activate"
|
||||
if not os.path.exists(systemd_activate):
|
||||
systemd_activate = "/lib/systemd/systemd-activate"
|
||||
if not os.path.exists(systemd_activate):
|
||||
print("Could not find systemd-activate")
|
||||
return
|
||||
self.aptly_server = self._start_process("%s -l %s aptly api serve -no-lock" %
|
||||
(systemd_activate, self.socket_path),)
|
||||
super(SystemdAPIHandoverTest, self).prepare()
|
||||
|
||||
def shutdown(self):
|
||||
if self.aptly_server is not None:
|
||||
self.aptly_server.terminate()
|
||||
self.aptly_server.wait()
|
||||
self.aptly_server = None
|
||||
if os.path.exists(self.socket_path):
|
||||
os.remove(self.socket_path)
|
||||
super(SystemdAPIHandoverTest, self).shutdown()
|
||||
|
||||
def run(self):
|
||||
pass
|
||||
|
||||
"""
|
||||
Verify we can listen on a unix domain socket.
|
||||
"""
|
||||
def check(self):
|
||||
if self.aptly_server is None:
|
||||
print("Skipping test as we failed to setup a listener.")
|
||||
return
|
||||
session = requests_unixsocket.Session()
|
||||
r = session.get('http+unix://%s/api/version' % urllib.quote(self.socket_path, safe=''))
|
||||
self.check_equal(r.json(), {'Version': os.environ['APTLY_VERSION']})
|
||||
@@ -0,0 +1,38 @@
|
||||
import requests_unixsocket
|
||||
import time
|
||||
import os
|
||||
import urllib
|
||||
|
||||
from lib import BaseTest
|
||||
|
||||
|
||||
class UnixSocketAPITest(BaseTest):
|
||||
aptly_server = None
|
||||
socket_path = "/tmp/_aptly_test.sock"
|
||||
base_url = ("unix://%s" % socket_path)
|
||||
|
||||
def prepare(self):
|
||||
if self.aptly_server is None:
|
||||
self.aptly_server = self._start_process("aptly api serve -no-lock -listen=%s" % (self.base_url),)
|
||||
time.sleep(1)
|
||||
super(UnixSocketAPITest, self).prepare()
|
||||
|
||||
def shutdown(self):
|
||||
if self.aptly_server is not None:
|
||||
self.aptly_server.terminate()
|
||||
self.aptly_server.wait()
|
||||
self.aptly_server = None
|
||||
super(UnixSocketAPITest, self).shutdown()
|
||||
|
||||
def run(self):
|
||||
pass
|
||||
|
||||
"""
|
||||
Verify we can listen on a unix domain socket.
|
||||
"""
|
||||
def check(self):
|
||||
session = requests_unixsocket.Session()
|
||||
r = session.get('http+unix://%s/api/version' % urllib.quote(UnixSocketAPITest.socket_path, safe=''))
|
||||
# Just needs to come back, we actually don't care much about the code.
|
||||
# Only needs to verify that the socket is actually responding.
|
||||
self.check_equal(r.json(), {'Version': os.environ['APTLY_VERSION']})
|
||||
@@ -0,0 +1,11 @@
|
||||
from api_lib import APITest
|
||||
import os
|
||||
|
||||
|
||||
class VersionAPITest(APITest):
|
||||
"""
|
||||
GET /version
|
||||
"""
|
||||
|
||||
def check(self):
|
||||
self.check_equal(self.get("/api/version").json(), {'Version': os.environ['APTLY_VERSION']})
|
||||
Reference in New Issue
Block a user