Merge pull request #62 from eReuse/feature/61-Json-Backup
Feature/61 json backup
This commit is contained in:
commit
7c0ccd5794
|
@ -116,3 +116,6 @@ ENV/
|
||||||
|
|
||||||
# Environment
|
# Environment
|
||||||
.env
|
.env
|
||||||
|
|
||||||
|
# Temporal dir
|
||||||
|
tmp/
|
||||||
|
|
|
@ -44,6 +44,9 @@ class DevicehubConfig(Config):
|
||||||
"""The minimum version of ereuse.org workbench that this devicehub
|
"""The minimum version of ereuse.org workbench that this devicehub
|
||||||
accepts. we recommend not changing this value.
|
accepts. we recommend not changing this value.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
TMP_SNAPSHOTS = config('TMP_SNAPSHOTS', '/tmp/snapshots')
|
||||||
|
"""This var is for save a snapshots in json format when fail something"""
|
||||||
API_DOC_CONFIG_TITLE = 'Devicehub'
|
API_DOC_CONFIG_TITLE = 'Devicehub'
|
||||||
API_DOC_CONFIG_VERSION = '0.2'
|
API_DOC_CONFIG_VERSION = '0.2'
|
||||||
API_DOC_CONFIG_COMPONENTS = {
|
API_DOC_CONFIG_COMPONENTS = {
|
||||||
|
|
|
@ -1,5 +1,9 @@
|
||||||
|
""" This is the view for Snapshots """
|
||||||
|
|
||||||
|
import os
|
||||||
|
import json
|
||||||
|
from datetime import datetime
|
||||||
from distutils.version import StrictVersion
|
from distutils.version import StrictVersion
|
||||||
from typing import List
|
|
||||||
from uuid import UUID
|
from uuid import UUID
|
||||||
|
|
||||||
from flask import current_app as app, request, g
|
from flask import current_app as app, request, g
|
||||||
|
@ -11,17 +15,43 @@ from ereuse_devicehub.db import db
|
||||||
from ereuse_devicehub.resources.action.models import Action, RateComputer, Snapshot, VisualTest, \
|
from ereuse_devicehub.resources.action.models import Action, RateComputer, Snapshot, VisualTest, \
|
||||||
InitTransfer
|
InitTransfer
|
||||||
from ereuse_devicehub.resources.action.rate.v1_0 import CannotRate
|
from ereuse_devicehub.resources.action.rate.v1_0 import CannotRate
|
||||||
from ereuse_devicehub.resources.device.models import Component, Computer
|
|
||||||
from ereuse_devicehub.resources.enums import SnapshotSoftware, Severity
|
from ereuse_devicehub.resources.enums import SnapshotSoftware, Severity
|
||||||
from ereuse_devicehub.resources.user.exceptions import InsufficientPermission
|
from ereuse_devicehub.resources.user.exceptions import InsufficientPermission
|
||||||
|
|
||||||
SUPPORTED_WORKBENCH = StrictVersion('11.0')
|
SUPPORTED_WORKBENCH = StrictVersion('11.0')
|
||||||
|
|
||||||
|
|
||||||
|
def save_json(req_json, tmp_snapshots, user):
|
||||||
|
"""
|
||||||
|
This function allow save a snapshot in json format un a TMP_SNAPSHOTS directory
|
||||||
|
The file need to be saved with one name format with the stamptime and uuid joins
|
||||||
|
"""
|
||||||
|
uuid = req_json.get('uuid', '')
|
||||||
|
now = datetime.now()
|
||||||
|
year = now.year
|
||||||
|
month = now.month
|
||||||
|
day = now.day
|
||||||
|
hour = now.hour
|
||||||
|
minutes = now.min
|
||||||
|
|
||||||
|
name_file = f"{year}-{month}-{day}-{hour}-{minutes}_{user}_{uuid}.json"
|
||||||
|
path_name = os.path.join(tmp_snapshots, name_file)
|
||||||
|
|
||||||
|
if not os.path.isdir(tmp_snapshots):
|
||||||
|
os.system('mkdir -p {}'.format(tmp_snapshots))
|
||||||
|
|
||||||
|
with open(path_name, 'w') as snapshot_file:
|
||||||
|
snapshot_file.write(json.dumps(req_json))
|
||||||
|
|
||||||
|
return path_name
|
||||||
|
|
||||||
|
|
||||||
class ActionView(View):
|
class ActionView(View):
|
||||||
def post(self):
|
def post(self):
|
||||||
"""Posts an action."""
|
"""Posts an action."""
|
||||||
json = request.get_json(validate=False)
|
json = request.get_json(validate=False)
|
||||||
|
tmp_snapshots = app.config['TMP_SNAPSHOTS']
|
||||||
|
path_snapshot = save_json(json, tmp_snapshots, g.user.email)
|
||||||
if not json or 'type' not in json:
|
if not json or 'type' not in json:
|
||||||
raise ValidationError('Resource needs a type.')
|
raise ValidationError('Resource needs a type.')
|
||||||
# todo there should be a way to better get subclassess resource
|
# todo there should be a way to better get subclassess resource
|
||||||
|
@ -29,11 +59,14 @@ class ActionView(View):
|
||||||
resource_def = app.resources[json['type']]
|
resource_def = app.resources[json['type']]
|
||||||
a = resource_def.schema.load(json)
|
a = resource_def.schema.load(json)
|
||||||
if json['type'] == Snapshot.t:
|
if json['type'] == Snapshot.t:
|
||||||
return self.snapshot(a, resource_def)
|
response = self.snapshot(a, resource_def)
|
||||||
|
os.remove(path_snapshot)
|
||||||
|
return response
|
||||||
if json['type'] == VisualTest.t:
|
if json['type'] == VisualTest.t:
|
||||||
pass
|
pass
|
||||||
# TODO JN add compute rate with new visual test and old components device
|
# TODO JN add compute rate with new visual test and old components device
|
||||||
if json['type'] == InitTransfer.t:
|
if json['type'] == InitTransfer.t:
|
||||||
|
os.remove(path_snapshot)
|
||||||
return self.transfer_ownership()
|
return self.transfer_ownership()
|
||||||
Model = db.Model._decl_class_registry.data[json['type']]()
|
Model = db.Model._decl_class_registry.data[json['type']]()
|
||||||
action = Model(**a)
|
action = Model(**a)
|
||||||
|
@ -42,6 +75,7 @@ class ActionView(View):
|
||||||
ret = self.schema.jsonify(action)
|
ret = self.schema.jsonify(action)
|
||||||
ret.status_code = 201
|
ret.status_code = 201
|
||||||
db.session.commit()
|
db.session.commit()
|
||||||
|
os.remove(path_snapshot)
|
||||||
return ret
|
return ret
|
||||||
|
|
||||||
def one(self, id: UUID):
|
def one(self, id: UUID):
|
||||||
|
|
|
@ -30,6 +30,7 @@ class TestConfig(DevicehubConfig):
|
||||||
SQLALCHEMY_DATABASE_URI = 'postgresql://dhub:ereuse@localhost/dh_test'
|
SQLALCHEMY_DATABASE_URI = 'postgresql://dhub:ereuse@localhost/dh_test'
|
||||||
TESTING = True
|
TESTING = True
|
||||||
SERVER_NAME = 'localhost'
|
SERVER_NAME = 'localhost'
|
||||||
|
TMP_SNAPSHOTS = '/tmp/snapshots'
|
||||||
|
|
||||||
|
|
||||||
@pytest.fixture(scope='session')
|
@pytest.fixture(scope='session')
|
||||||
|
|
|
@ -0,0 +1,30 @@
|
||||||
|
type: Snapshot
|
||||||
|
uuid: 9a3e7485-fdd0-47ce-bcc7-65c55226b598
|
||||||
|
version: '11.0b9'
|
||||||
|
software: Workbench
|
||||||
|
elapsed: 4
|
||||||
|
device:
|
||||||
|
type: Desktop
|
||||||
|
chassis: Microtower
|
||||||
|
serialNumber: null
|
||||||
|
model: null
|
||||||
|
manufacturer: null
|
||||||
|
actions:
|
||||||
|
- type: VisualTest
|
||||||
|
appearanceRange: A
|
||||||
|
functionalityRange: B
|
||||||
|
components:
|
||||||
|
- type: RamModule
|
||||||
|
serialNumber: rm1s
|
||||||
|
model: rm1ml
|
||||||
|
manufacturer: rm1mr
|
||||||
|
speed: 1333
|
||||||
|
- type: Processor
|
||||||
|
serialNumber: p1s
|
||||||
|
model: p1ml
|
||||||
|
manufacturer: p1mr
|
||||||
|
speed: 1.6
|
||||||
|
actions:
|
||||||
|
- type: BenchmarkProcessorr
|
||||||
|
rate: 2410
|
||||||
|
elapsed: 11
|
|
@ -0,0 +1,36 @@
|
||||||
|
type: Snapshot
|
||||||
|
uuid: 62b3e393-0c25-42cf-a5fa-ab796fac76dd
|
||||||
|
version: 11.0
|
||||||
|
software: Workbench
|
||||||
|
elapsed: 4
|
||||||
|
device:
|
||||||
|
type: Laptop
|
||||||
|
chassis: Notebook
|
||||||
|
serialNumber: d6s
|
||||||
|
model: d6ml
|
||||||
|
manufacturer: d6mr
|
||||||
|
components:
|
||||||
|
- type: RamModule
|
||||||
|
serialNumber: rm6s
|
||||||
|
model: rm6ml
|
||||||
|
manufacturer: rm6mr
|
||||||
|
speed: 1333
|
||||||
|
- type: Processor
|
||||||
|
serialNumber: p6s
|
||||||
|
model: p6ml
|
||||||
|
manufacturer: p6mr
|
||||||
|
speed: 1.6
|
||||||
|
actions:
|
||||||
|
- type: BenchmarkProcessor
|
||||||
|
rate: 2410
|
||||||
|
elapsed: 11
|
||||||
|
- type: HardDrive
|
||||||
|
size: 160041.88569599998
|
||||||
|
model: hdd4m
|
||||||
|
manufacturer: hdd4mr
|
||||||
|
serialNumber: hdd4s
|
||||||
|
actions:
|
||||||
|
- type: BenchmarkDataStorage
|
||||||
|
elapsed: 22
|
||||||
|
writeSpeed: 17.3
|
||||||
|
readSpeed: 41.6
|
|
@ -0,0 +1,36 @@
|
||||||
|
type: Snapshot
|
||||||
|
uuid: 81e1f340-5aac-4619-931b-d312e4866cb7
|
||||||
|
version: 11.0
|
||||||
|
software: Workbench
|
||||||
|
elapsed: 4
|
||||||
|
device:
|
||||||
|
type: Laptop
|
||||||
|
chassis: null
|
||||||
|
serialNumber: d5s
|
||||||
|
model: d5ml
|
||||||
|
manufacturer: d5mr
|
||||||
|
components:
|
||||||
|
- type: RamModule
|
||||||
|
serialNumber: rm5s
|
||||||
|
model: rm5ml
|
||||||
|
manufacturer: rm5mr
|
||||||
|
speed: 1333
|
||||||
|
type: Processor
|
||||||
|
serialNumber: p5s
|
||||||
|
model: p5ml
|
||||||
|
manufacturer: p5mr
|
||||||
|
speed: 1.6
|
||||||
|
actions:
|
||||||
|
- type: BenchmarkProcessor
|
||||||
|
rate: 2410
|
||||||
|
elapsed: 11
|
||||||
|
size: 160041.88569599998
|
||||||
|
model: hdd5m
|
||||||
|
type: HardDrive
|
||||||
|
manufacturer: hdd5mr
|
||||||
|
serialNumber: hdd5s
|
||||||
|
actions:
|
||||||
|
- type: BenchmarkDataStorage
|
||||||
|
elapsed: 22
|
||||||
|
writeSpeed: 17.3
|
||||||
|
readSpeed: 41.6
|
|
@ -0,0 +1,22 @@
|
||||||
|
type: Snapshot
|
||||||
|
uuid: 127fad1c-a3f2-4677-9dab-4a370071a882
|
||||||
|
version: 11.0
|
||||||
|
software: Workbench
|
||||||
|
elapsed: 4
|
||||||
|
device:
|
||||||
|
type: Laptop
|
||||||
|
chassis: Microtower
|
||||||
|
serialNumber: d2s
|
||||||
|
model: d2ml
|
||||||
|
manufacturer: d2mr
|
||||||
|
components:
|
||||||
|
- type: RamModule
|
||||||
|
serialNumber: rm2s
|
||||||
|
model: rm2ml
|
||||||
|
manufacturer: rm2mr
|
||||||
|
speed: 1333
|
||||||
|
- type: Processor
|
||||||
|
serialNumber: p2s
|
||||||
|
model: p2ml
|
||||||
|
manufacturer: p2mr
|
||||||
|
speed: 1.6
|
|
@ -0,0 +1,31 @@
|
||||||
|
type: Snapshot
|
||||||
|
uuid: 2afa5413-9858-4577-8273-a027a647fed0
|
||||||
|
version: 11.0
|
||||||
|
software: Workbench
|
||||||
|
elapsed: 4
|
||||||
|
device:
|
||||||
|
type: Desktop
|
||||||
|
chassis: Microtower
|
||||||
|
serialNumber: d3s
|
||||||
|
model: d3ml
|
||||||
|
manufacturer: d3mr
|
||||||
|
components:
|
||||||
|
- type: RamModule
|
||||||
|
serialNumber: rm3s
|
||||||
|
model: rm3ml
|
||||||
|
manufacturer: rm3mr
|
||||||
|
speed: 1333
|
||||||
|
- type: Processor
|
||||||
|
serialNumber: p3s
|
||||||
|
model: p3ml
|
||||||
|
manufacturer: p3mr
|
||||||
|
speed: 1.6
|
||||||
|
size: 160041.88569599998
|
||||||
|
model: hdd3m
|
||||||
|
type: HardDrive
|
||||||
|
manufacturer: hdd3mr
|
||||||
|
serialNumber: hdd3s
|
||||||
|
actions:
|
||||||
|
- type: BenchmarkProcessor
|
||||||
|
rate: 2410
|
||||||
|
elapsed: 11
|
|
@ -1,9 +1,13 @@
|
||||||
|
import os
|
||||||
|
import json
|
||||||
|
import pytest
|
||||||
|
|
||||||
from datetime import datetime, timedelta, timezone
|
from datetime import datetime, timedelta, timezone
|
||||||
|
from requests.exceptions import HTTPError
|
||||||
from operator import itemgetter
|
from operator import itemgetter
|
||||||
from typing import List, Tuple
|
from typing import List, Tuple
|
||||||
from uuid import uuid4
|
from uuid import uuid4
|
||||||
|
|
||||||
import pytest
|
|
||||||
from boltons import urlutils
|
from boltons import urlutils
|
||||||
from teal.db import UniqueViolation, DBError
|
from teal.db import UniqueViolation, DBError
|
||||||
from teal.marshmallow import ValidationError
|
from teal.marshmallow import ValidationError
|
||||||
|
@ -22,6 +26,7 @@ from ereuse_devicehub.resources.device.sync import MismatchBetweenProperties, \
|
||||||
from ereuse_devicehub.resources.enums import ComputerChassis, SnapshotSoftware
|
from ereuse_devicehub.resources.enums import ComputerChassis, SnapshotSoftware
|
||||||
from ereuse_devicehub.resources.tag import Tag
|
from ereuse_devicehub.resources.tag import Tag
|
||||||
from ereuse_devicehub.resources.user.models import User
|
from ereuse_devicehub.resources.user.models import User
|
||||||
|
from ereuse_devicehub.resources.action.views import save_json
|
||||||
from tests.conftest import file
|
from tests.conftest import file
|
||||||
|
|
||||||
|
|
||||||
|
@ -473,3 +478,147 @@ def test_pc_rating_rate_none(user: UserClient):
|
||||||
def test_pc_2(user: UserClient):
|
def test_pc_2(user: UserClient):
|
||||||
s = file('laptop-hp_255_g3_notebook-hewlett-packard-cnd52270fw.snapshot')
|
s = file('laptop-hp_255_g3_notebook-hewlett-packard-cnd52270fw.snapshot')
|
||||||
snapshot, _ = user.post(res=Snapshot, data=s)
|
snapshot, _ = user.post(res=Snapshot, data=s)
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.mvp
|
||||||
|
def test_save_snapshot_in_file(app: Devicehub, user: UserClient):
|
||||||
|
""" This test check if works the function save_snapshot_in_file """
|
||||||
|
tmp_snapshots = app.config['TMP_SNAPSHOTS']
|
||||||
|
snapshot_no_hid = file('basic.snapshot.nohid')
|
||||||
|
save_json(snapshot_no_hid, tmp_snapshots, user.user['email'])
|
||||||
|
|
||||||
|
uuid = snapshot_no_hid['uuid']
|
||||||
|
files = [x for x in os.listdir(tmp_snapshots) if uuid in x]
|
||||||
|
|
||||||
|
snapshot = {'software': '', 'version': '', 'uuid': ''}
|
||||||
|
if files:
|
||||||
|
path_snapshot = os.path.join(tmp_snapshots, files[0])
|
||||||
|
with open(path_snapshot) as file_snapshot:
|
||||||
|
snapshot = json.loads(file_snapshot.read())
|
||||||
|
|
||||||
|
os.remove(path_snapshot)
|
||||||
|
|
||||||
|
assert snapshot['software'] == snapshot_no_hid['software']
|
||||||
|
assert snapshot['version'] == snapshot_no_hid['version']
|
||||||
|
assert snapshot['uuid'] == uuid
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.mvp
|
||||||
|
def test_backup_snapshot_with_errors(app: Devicehub, user: UserClient):
|
||||||
|
""" This test check if the file snapshot is create when some snapshot is wrong """
|
||||||
|
tmp_snapshots = app.config['TMP_SNAPSHOTS']
|
||||||
|
snapshot_no_hid = file('basic.snapshot.badly_formed')
|
||||||
|
uuid = snapshot_no_hid['uuid']
|
||||||
|
|
||||||
|
snapshot = {'software': '', 'version': '', 'uuid': ''}
|
||||||
|
with pytest.raises(KeyError):
|
||||||
|
response = user.post(res=Snapshot, data=snapshot_no_hid)
|
||||||
|
|
||||||
|
files = [x for x in os.listdir(tmp_snapshots) if uuid in x]
|
||||||
|
if files:
|
||||||
|
path_snapshot = os.path.join(tmp_snapshots, files[0])
|
||||||
|
with open(path_snapshot) as file_snapshot:
|
||||||
|
snapshot = json.loads(file_snapshot.read())
|
||||||
|
|
||||||
|
os.remove(path_snapshot)
|
||||||
|
|
||||||
|
assert snapshot['software'] == snapshot_no_hid['software']
|
||||||
|
assert snapshot['version'] == snapshot_no_hid['version']
|
||||||
|
assert snapshot['uuid'] == uuid
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.mvp
|
||||||
|
def test_snapshot_failed_missing_cpu_benchmark(app: Devicehub, user: UserClient):
|
||||||
|
""" This test check if the file snapshot is create when some snapshot is wrong """
|
||||||
|
tmp_snapshots = app.config['TMP_SNAPSHOTS']
|
||||||
|
snapshot_error = file('failed.snapshot.500.missing-cpu-benchmark')
|
||||||
|
uuid = snapshot_error['uuid']
|
||||||
|
|
||||||
|
snapshot = {'software': '', 'version': '', 'uuid': ''}
|
||||||
|
with pytest.raises(TypeError):
|
||||||
|
user.post(res=Snapshot, data=snapshot_error)
|
||||||
|
|
||||||
|
files = [x for x in os.listdir(tmp_snapshots) if uuid in x]
|
||||||
|
if files:
|
||||||
|
path_snapshot = os.path.join(tmp_snapshots, files[0])
|
||||||
|
with open(path_snapshot) as file_snapshot:
|
||||||
|
snapshot = json.loads(file_snapshot.read())
|
||||||
|
|
||||||
|
os.remove(path_snapshot)
|
||||||
|
|
||||||
|
assert snapshot['software'] == snapshot_error['software']
|
||||||
|
assert snapshot['version'] == snapshot_error['version']
|
||||||
|
assert snapshot['uuid'] == uuid
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.mvp
|
||||||
|
def test_snapshot_failed_missing_hdd_benchmark(app: Devicehub, user: UserClient):
|
||||||
|
""" This test check if the file snapshot is create when some snapshot is wrong """
|
||||||
|
tmp_snapshots = app.config['TMP_SNAPSHOTS']
|
||||||
|
snapshot_error = file('failed.snapshot.500.missing-hdd-benchmark')
|
||||||
|
uuid = snapshot_error['uuid']
|
||||||
|
|
||||||
|
snapshot = {'software': '', 'version': '', 'uuid': ''}
|
||||||
|
with pytest.raises(TypeError):
|
||||||
|
user.post(res=Snapshot, data=snapshot_error)
|
||||||
|
|
||||||
|
files = [x for x in os.listdir(tmp_snapshots) if uuid in x]
|
||||||
|
if files:
|
||||||
|
path_snapshot = os.path.join(tmp_snapshots, files[0])
|
||||||
|
with open(path_snapshot) as file_snapshot:
|
||||||
|
snapshot = json.loads(file_snapshot.read())
|
||||||
|
|
||||||
|
os.remove(path_snapshot)
|
||||||
|
|
||||||
|
assert snapshot['software'] == snapshot_error['software']
|
||||||
|
assert snapshot['version'] == snapshot_error['version']
|
||||||
|
assert snapshot['uuid'] == uuid
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.mvp
|
||||||
|
def test_snapshot_failed_null_chassis(app: Devicehub, user: UserClient):
|
||||||
|
""" This test check if the file snapshot is create when some snapshot is wrong """
|
||||||
|
tmp_snapshots = app.config['TMP_SNAPSHOTS']
|
||||||
|
snapshot_error = file('failed.snapshot.422.null-chassis')
|
||||||
|
uuid = snapshot_error['uuid']
|
||||||
|
|
||||||
|
snapshot = {'software': '', 'version': '', 'uuid': ''}
|
||||||
|
with pytest.raises(TypeError):
|
||||||
|
user.post(res=Snapshot, data=snapshot_error)
|
||||||
|
|
||||||
|
files = [x for x in os.listdir(tmp_snapshots) if uuid in x]
|
||||||
|
if files:
|
||||||
|
path_snapshot = os.path.join(tmp_snapshots, files[0])
|
||||||
|
with open(path_snapshot) as file_snapshot:
|
||||||
|
snapshot = json.loads(file_snapshot.read())
|
||||||
|
|
||||||
|
os.remove(path_snapshot)
|
||||||
|
|
||||||
|
assert snapshot['software'] == snapshot_error['software']
|
||||||
|
assert snapshot['version'] == snapshot_error['version']
|
||||||
|
assert snapshot['uuid'] == uuid
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.mvp
|
||||||
|
def test_snapshot_failed_missing_chassis(app: Devicehub, user: UserClient):
|
||||||
|
""" This test check if the file snapshot is create when some snapshot is wrong """
|
||||||
|
tmp_snapshots = app.config['TMP_SNAPSHOTS']
|
||||||
|
snapshot_error = file('failed.snapshot.422.missing-chassis')
|
||||||
|
uuid = snapshot_error['uuid']
|
||||||
|
|
||||||
|
snapshot = {'software': '', 'version': '', 'uuid': ''}
|
||||||
|
with pytest.raises(TypeError):
|
||||||
|
user.post(res=Snapshot, data=snapshot_error)
|
||||||
|
|
||||||
|
files = [x for x in os.listdir(tmp_snapshots) if uuid in x]
|
||||||
|
if files:
|
||||||
|
path_snapshot = os.path.join(tmp_snapshots, files[0])
|
||||||
|
with open(path_snapshot) as file_snapshot:
|
||||||
|
snapshot = json.loads(file_snapshot.read())
|
||||||
|
|
||||||
|
os.remove(path_snapshot)
|
||||||
|
|
||||||
|
assert snapshot['software'] == snapshot_error['software']
|
||||||
|
assert snapshot['version'] == snapshot_error['version']
|
||||||
|
assert snapshot['uuid'] == uuid
|
||||||
|
|
||||||
|
|
Reference in New Issue