Skip to content
Toggle navigation
P
Projects
G
Groups
S
Snippets
Help
CIRCLE
/
cloud
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
94
Merge Requests
10
Pipelines
Wiki
Snippets
Members
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Commit
89f43b4b
authored
7 years ago
by
Fukász Rómeó Ervin
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
refactor occi api views and classes
parent
5a4b3e24
Pipeline
#615
failed with stage
in 0 seconds
Changes
9
Pipelines
1
Hide whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
680 additions
and
295 deletions
+680
-295
circle/occi/client_example.py
+235
-104
circle/occi/core.py
+56
-60
circle/occi/infrastructure.py
+82
-7
circle/occi/instances.py
+72
-5
circle/occi/migrations/__init__.py
+0
-0
circle/occi/mixins.py
+19
-0
circle/occi/urls.py
+16
-4
circle/occi/utils.py
+22
-33
circle/occi/views.py
+178
-82
No files found.
circle/occi/
occi_
client_example.py
→
circle/occi/client_example.py
View file @
89f43b4b
...
...
@@ -24,8 +24,25 @@ import json
# kikapcsoljuk a figyelmezteteseket
# urllib3.disable_warnings()
def
dumps
(
*
args
,
**
kwargs
):
try
:
return
json
.
dumps
(
*
args
,
**
kwargs
)
except
Exception
as
e
:
print
(
e
)
return
{}
def
loads
(
*
args
,
**
kwargs
):
try
:
return
json
.
loads
(
*
args
,
**
kwargs
)
except
Exception
as
e
:
print
(
e
)
return
{}
# A szerver base url-je es a felhasznalo adatai
server
=
"https://
vm.ik.bme.hu:15766
/"
server
=
"https://
localhost
/"
username
=
"admin"
password
=
"retekretek"
loginData
=
{
"username"
:
username
,
"password"
:
password
}
...
...
@@ -42,8 +59,8 @@ with requests.Session() as session:
print
(
"----------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# Bejelentkezes
...
...
@@ -52,13 +69,58 @@ with requests.Session() as session:
# a cookie-ban
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
'csrftoken'
]
req
=
session
.
post
(
server
+
"occi/login/"
,
verify
=
False
,
data
=
json
.
dumps
(
loginData
),
headers
=
headers
)
data
=
dumps
(
loginData
),
headers
=
headers
)
print
(
"login"
)
print
(
"-----"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
'csrftoken'
]
req
=
session
.
get
(
server
+
"occi/token/"
,
verify
=
False
,
headers
=
headers
)
print
(
"token"
)
print
(
"-----"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
token
=
req
.
json
()[
"token"
]
req
=
session
.
get
(
server
+
"occi/test/?token="
+
token
,
verify
=
False
,
headers
=
headers
)
print
(
"token-use"
)
print
(
"---------"
)
print
(
server
+
"occi/test/?token="
+
token
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
req
=
session
.
get
(
server
+
"occi/test/?token=asdasdasd"
+
token
,
verify
=
False
,
headers
=
headers
)
print
(
"token-use"
)
print
(
"---------"
)
print
(
server
+
"occi/test/?token="
+
token
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
exit
()
# storage creation wrong
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
'csrftoken'
]
req
=
session
.
put
(
server
+
"occi/storage/100"
,
verify
=
False
,
data
=
dumps
({}),
headers
=
headers
)
print
(
"storage_creation_wrong"
)
print
(
"---------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# query interface
...
...
@@ -67,8 +129,8 @@ with requests.Session() as session:
print
(
"---------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# osszes vm collectionkent
...
...
@@ -78,24 +140,24 @@ with requests.Session() as session:
print
(
"------------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# az elso vm a listabol
vmid
=
json
.
loads
(
req
.
text
)[
"resources"
][
0
][
"id"
]
vmid
=
loads
(
req
.
text
)[
"resources"
][
0
][
"id"
]
req
=
session
.
get
(
server
+
"occi/compute/"
+
vmid
+
"/"
,
headers
=
headers
,
verify
=
False
)
print
(
"compute-"
+
str
(
vmid
))
print
(
"------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# ha nem active, akkor azza tesszuk
state
=
json
.
loads
(
req
.
text
)[
"attributes"
][
"occi.compute.state"
]
state
=
loads
(
req
.
text
)[
"attributes"
][
"occi.compute.state"
]
action
=
"http://schemas.ogf.org/occi/infrastructure/compute/action#"
if
state
!=
"active"
:
try
:
...
...
@@ -104,52 +166,52 @@ with requests.Session() as session:
pass
req
=
session
.
post
(
server
+
"occi/compute/"
+
vmid
+
"/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
({
"action"
:
action
+
"start"
}))
data
=
dumps
({
"action"
:
action
+
"start"
}))
print
(
"compute-"
+
str
(
vmid
)
+
"-start"
)
print
(
"---------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# restart
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
'csrftoken'
]
except
:
pass
actionatrs
=
{
"method"
:
"
warm
"
}
#
# restart
#
try:
#
headers["X-CSRFToken"] = req.cookies['csrftoken']
#
except:
#
pass
actionatrs
=
{
"method"
:
"
cold
"
}
actioninv
=
{
"action"
:
action
+
"restart"
,
"attributes"
:
actionatrs
}
req
=
session
.
post
(
server
+
"occi/compute/"
+
vmid
+
"/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
(
actioninv
))
print
(
"compute-"
+
str
(
vmid
)
+
"-restart"
)
print
(
"-----------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
#
req = session.post(server + "occi/compute/" + vmid + "/",
#
headers=headers, verify=False,
# data=
dumps(actioninv))
#
print("compute-" + str(vmid) + "-restart")
#
print("-----------------")
#
print("status_code: " + str(req.status_code))
#
print
# print(dumps(
loads(req.text), sort_keys=True,
#
indent=4, separators=(",", ": ")))
#
print
# s
uspend
# s
top
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
'csrftoken'
]
except
:
pass
actioninv
[
"action"
]
=
action
+
"stop"
actioninv
[
"attributes"
][
"method"
]
=
"
graceful
"
actioninv
[
"attributes"
][
"method"
]
=
"
poweroff
"
req
=
session
.
post
(
server
+
"occi/compute/"
+
vmid
+
"/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
(
actioninv
))
data
=
dumps
(
actioninv
))
print
(
"compute-"
+
str
(
vmid
)
+
"-stop"
)
print
(
"-----------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
#
nem letezo
action
#
renew
action
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
"csrftoken"
]
except
:
...
...
@@ -157,103 +219,172 @@ with requests.Session() as session:
actioninv
[
"action"
]
=
action
+
"renew"
req
=
session
.
post
(
server
+
"occi/compute/"
+
vmid
+
"/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
(
actioninv
))
data
=
dumps
(
actioninv
))
print
(
"compute-"
+
str
(
vmid
)
+
"-renew"
)
print
(
"-------------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# vm krealas
# networkinterface add interface
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
"csrftoken"
]
except
:
pass
# a template mixinje benne kell legyen az adatokban
# az osszes template a query interfacen megjelenik mint mixin
# azok a mixinek templatek amik az os_tpl mixintol fuggnek
putdata
=
{
"mixins"
:
[
"http://circlecloud.org/occi/templates/os#os_template_1"
],
"other_occi_compute_data"
:
"may be provided"
}
req
=
session
.
put
(
server
+
"occi/compute/1/"
,
req
=
session
.
put
(
server
+
"occi/networkinterface/compute"
+
vmid
+
"-network3/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
(
putdata
))
print
(
"
create_compute
"
)
print
(
"--------------"
)
data
=
dumps
({}
))
print
(
"
nif-creation
"
)
print
(
"--------------
-----
"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# vm torles
# networkinterface addport
actionatrs
=
{
"protocol"
:
"tcp"
,
"port"
:
1111
}
actioninv
=
{
"action"
:
"addport"
,
"attributes"
:
actionatrs
}
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
"csrftoken"
]
except
:
pass
vmid
=
json
.
loads
(
req
.
text
)[
"id"
]
req
=
session
.
delete
(
server
+
"occi/compute/"
+
vmid
+
"/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
(
putdata
))
print
(
"delete_compute"
)
print
(
"--------------"
)
req
=
session
.
post
(
server
+
"occi/networkinterface/compute"
+
vmid
+
"-network3/"
,
headers
=
headers
,
verify
=
False
,
data
=
dumps
(
actioninv
))
print
(
"networkinterface-addport"
)
print
(
"-------------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
# networkinterface removeport
actionatrs
=
{
"protocol"
:
"tcp"
,
"port"
:
1111
}
actioninv
=
{
"action"
:
"removeport"
,
"attributes"
:
actionatrs
}
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
"csrftoken"
]
except
:
pass
req
=
session
.
get
(
server
+
"occi/network/1/"
,
headers
=
headers
,
verify
=
False
)
print
(
"storage"
)
print
(
"-------"
)
print
(
"status_code "
+
str
(
req
.
status_code
))
req
=
session
.
post
(
server
+
"occi/networkinterface/compute"
+
vmid
+
"-network3/"
,
headers
=
headers
,
verify
=
False
,
data
=
dumps
(
actioninv
))
print
(
"networkinterface-addport"
)
print
(
"-------------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
"csrftoken"
]
except
:
pass
req
=
session
.
post
(
server
+
"occi/network/1/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
({
"action"
:
"online"
}))
print
(
"storage"
)
print
(
"-------"
)
print
(
"status_code "
+
str
(
req
.
status_code
))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
# networkinterface remove interface
try
:
headers
[
"X-CSRFToken"
]
=
req
.
cookies
[
"csrftoken"
]
except
:
pass
req
=
session
.
post
(
server
+
"occi/compute/96/"
,
headers
=
headers
,
verify
=
False
,
data
=
json
.
dumps
(
{
"attributes"
:
{
"occi.compute.memory"
:
0.250
}
}))
print
(
"computerehelelel"
)
print
(
"-------"
)
print
(
"status_code "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
# Kijelentkezes
req
=
session
.
get
(
server
+
"occi/logout/"
,
headers
=
headers
,
verify
=
False
)
print
(
"logout"
)
print
(
"------"
)
req
=
session
.
delete
(
server
+
"occi/networkinterface/compute"
+
vmid
+
"-network3/"
,
headers
=
headers
,
verify
=
False
)
print
(
"nif-creation"
)
print
(
"-------------------"
)
print
(
"status_code: "
+
str
(
req
.
status_code
))
print
print
(
json
.
dumps
(
json
.
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
(
dumps
(
loads
(
req
.
text
),
sort_keys
=
True
,
indent
=
4
,
separators
=
(
","
,
": "
)))
print
#
# # vm krealas
# try:
# headers["X-CSRFToken"] = req.cookies["csrftoken"]
# except:
# pass
# # a template mixinje benne kell legyen az adatokban
# # az osszes template a query interfacen megjelenik mint mixin
# # azok a mixinek templatek amik az os_tpl mixintol fuggnek
# putdata = {"mixins": [
# "http://circlecloud.org/occi/templates/os#os_template_1"],
# "other_occi_compute_data": "may be provided"}
# req = session.put(server + "occi/compute/1/",
# headers=headers, verify=False,
# data=dumps(putdata))
# print("create_compute")
# print("--------------")
# print("status_code: " + str(req.status_code))
# print
# print(dumps(loads(req.text), sort_keys=True,
# indent=4, separators=(",", ": ")))
# print
#
# # vm torles
# try:
# headers["X-CSRFToken"] = req.cookies["csrftoken"]
# except:
# pass
# vmid = loads(req.text)["id"]
# req = session.delete(server + "occi/compute/" + vmid + "/",
# headers=headers, verify=False,
# data=dumps(putdata))
# print("delete_compute")
# print("--------------")
# print("status_code: " + str(req.status_code))
# print
# print(dumps(loads(req.text), sort_keys=True,
# indent=4, separators=(",", ": ")))
# print
#
# try:
# headers["X-CSRFToken"] = req.cookies["csrftoken"]
# except:
# pass
# req = session.get(server + "occi/network/1/", headers=headers,
# verify=False)
# print("storage")
# print("-------")
# print("status_code " + str(req.status_code))
# print
# print(dumps(loads(req.text), sort_keys=True,
# indent=4, separators=(",", ": ")))
#
# try:
# headers["X-CSRFToken"] = req.cookies["csrftoken"]
# except:
# pass
# req = session.post(server + "occi/network/1/", headers=headers,
# verify=False, data=dumps({"action": "online"}))
# print("storage")
# print("-------")
# print("status_code " + str(req.status_code))
# print
# print(dumps(loads(req.text), sort_keys=True,
# indent=4, separators=(",", ": ")))
#
# try:
# headers["X-CSRFToken"] = req.cookies["csrftoken"]
# except:
# pass
# req = session.post(server + "occi/compute/96/", headers=headers,
# verify=False, data=dumps(
# {
# "attributes": {
# "occi.compute.memory": 0.250
# }
# }))
# print("computerehelelel")
# print("-------")
# print("status_code " + str(req.status_code))
# print
# print(dumps(loads(req.text), sort_keys=True,
# indent=4, separators=(",", ": ")))
#
# # Kijelentkezes
# req = session.get(server + "occi/logout/", headers=headers,
# verify=False)
# print("logout")
# print("------")
# print("status_code: " + str(req.status_code))
# print
# print(dumps(loads(req.text), sort_keys=True,
# indent=4, separators=(",", ": ")))
This diff is collapsed.
Click to expand it.
circle/occi/
occi_
core.py
→
circle/occi/core.py
View file @
89f43b4b
...
...
@@ -19,10 +19,10 @@
""" Implementation of the OCCI - Core model classes """
from
occi
_
utils
import
set_optional_attributes
from
occi
.
utils
import
set_optional_attributes
class
Attribute
:
class
Attribute
(
object
)
:
""" OCCI 1.2 - CORE - Classification - Attribute """
TYPES
=
(
"Object"
,
"List"
,
"Hash"
)
...
...
@@ -36,16 +36,16 @@ class Attribute:
self
.
required
=
required
set_optional_attributes
(
self
,
self
.
optional_attributes
,
kwargs
)
def
render_as_json
(
self
):
json
=
{
"mutable"
:
self
.
mutable
,
"required"
:
self
.
required
,
"type"
:
self
.
type
}
def
as_dict
(
self
):
res
=
{
"mutable"
:
self
.
mutable
,
"required"
:
self
.
required
,
"type"
:
self
.
type
}
if
hasattr
(
self
,
"pattern"
):
json
[
"pattern"
]
=
self
.
pattern
res
[
"pattern"
]
=
self
.
pattern
if
hasattr
(
self
,
"default"
):
json
[
"default"
]
=
self
.
default
res
[
"default"
]
=
self
.
default
if
hasattr
(
self
,
"description"
):
json
[
"description"
]
=
self
.
description
return
json
res
[
"description"
]
=
self
.
description
return
res
class
Category
(
object
):
...
...
@@ -71,24 +71,23 @@ class Kind(Category):
set_optional_attributes
(
self
,
self
.
kind_optional_attributes
,
kwargs
)
def
render_as_json
(
self
):
json
=
{
"term"
:
self
.
term
,
"scheme"
:
self
.
scheme
}
def
as_dict
(
self
):
res
=
{
"term"
:
self
.
term
,
"scheme"
:
self
.
scheme
}
if
hasattr
(
self
,
"title"
):
json
[
"title"
]
=
self
.
title
res
[
"title"
]
=
self
.
title
if
hasattr
(
self
,
"parent"
):
json
[
"parent"
]
=
self
.
parent
res
[
"parent"
]
=
self
.
parent
if
hasattr
(
self
,
"location"
):
json
[
"location"
]
=
self
.
location
res
[
"location"
]
=
self
.
location
if
hasattr
(
self
,
"attributes"
):
json
[
"attributes"
]
=
{}
res
[
"attributes"
]
=
{}
for
attribute
in
self
.
attributes
:
json
[
"attributes"
][
attribute
.
name
]
=
(
attribute
.
render_as_json
())
res
[
"attributes"
][
attribute
.
name
]
=
(
attribute
.
as_dict
())
if
hasattr
(
self
,
"actions"
):
json
[
"actions"
]
=
[]
res
[
"actions"
]
=
[]
for
action
in
self
.
actions
:
json
[
"actions"
]
.
append
(
action
.
scheme
+
action
.
term
)
return
json
res
[
"actions"
]
.
append
(
action
.
scheme
+
action
.
term
)
return
res
class
Action
(
Category
):
...
...
@@ -97,16 +96,15 @@ class Action(Category):
def
__init
(
self
,
*
args
,
**
kwargs
):
super
(
Action
,
self
)
.
__init__
(
*
args
,
**
kwargs
)
def
render_as_json
(
self
):
json
=
{
"term"
:
self
.
term
,
"scheme"
:
self
.
scheme
}
def
as_dict
(
self
):
res
=
{
"term"
:
self
.
term
,
"scheme"
:
self
.
scheme
}
if
hasattr
(
self
,
"title"
):
json
[
"title"
]
=
self
.
title
res
[
"title"
]
=
self
.
title
if
hasattr
(
self
,
"attributes"
):
json
[
"attributes"
]
=
{}
res
[
"attributes"
]
=
{}
for
attribute
in
self
.
attributes
:
json
[
"attributes"
][
attribute
.
name
]
=
(
attribute
.
render_as_json
())
return
json
res
[
"attributes"
][
attribute
.
name
]
=
(
attribute
.
as_dict
())
return
res
class
Mixin
(
Category
):
...
...
@@ -120,26 +118,25 @@ class Mixin(Category):
set_optional_attributes
(
self
,
self
.
mixin_optional_attributes
,
kwargs
)
def
render_as_json
(
self
):
json
=
{
"term"
:
self
.
term
,
"scheme"
:
self
.
scheme
}
def
as_dict
(
self
):
res
=
{
"term"
:
self
.
term
,
"scheme"
:
self
.
scheme
}
if
hasattr
(
self
,
"title"
):
json
[
"title"
]
=
self
.
title
res
[
"title"
]
=
self
.
title
if
hasattr
(
self
,
"location"
):
json
[
"location"
]
=
self
.
location
res
[
"location"
]
=
self
.
location
if
hasattr
(
self
,
"depends"
):
json
[
"depends"
]
=
self
.
depends
res
[
"depends"
]
=
self
.
depends
if
hasattr
(
self
,
"applies"
):
json
[
"applies"
]
=
self
.
applies
res
[
"applies"
]
=
self
.
applies
if
hasattr
(
self
,
"attributes"
):
json
[
"attributes"
]
=
{}
res
[
"attributes"
]
=
{}
for
attribute
in
self
.
attributes
:
json
[
"attributes"
][
attribute
.
name
]
=
(
attribute
.
render_as_json
())
res
[
"attributes"
][
attribute
.
name
]
=
(
attribute
.
as_dict
())
if
hasattr
(
self
,
"actions"
):
json
[
"actions"
]
=
[]
res
[
"actions"
]
=
[]
for
action
in
self
.
actions
:
json
[
"actions"
]
.
append
(
action
.
scheme
+
action
.
term
)
return
json
res
[
"actions"
]
.
append
(
action
.
scheme
+
action
.
term
)
return
res
class
Entity
(
object
):
...
...
@@ -161,24 +158,24 @@ class Resource(Entity):
def
__init__
(
self
,
*
args
,
**
kwargs
):
super
(
Resource
,
self
)
.
__init__
(
*
args
,
**
kwargs
)
set_optional_attributes
(
self
,
self
.
resource_optional_attributes
,
kwargs
)
set_optional_attributes
(
self
,
self
.
resource_optional_attributes
,
kwargs
)
def
render_as_json
(
self
):
json
=
{
"kind"
:
self
.
kind
,
"id"
:
self
.
id
}
def
as_dict
(
self
):
res
=
{
"kind"
:
self
.
kind
,
"id"
:
self
.
id
}
if
hasattr
(
self
,
"title"
):
json
[
"title"
]
=
self
.
title
res
[
"title"
]
=
self
.
title
if
hasattr
(
self
,
"summary"
):
json
[
"summary"
]
=
self
.
summary
res
[
"summary"
]
=
self
.
summary
if
hasattr
(
self
,
"attributes"
):
json
[
"attributes"
]
=
self
.
attributes
res
[
"attributes"
]
=
self
.
attributes
if
hasattr
(
self
,
"actions"
):
json
[
"actions"
]
=
self
.
actions
res
[
"actions"
]
=
self
.
actions
if
hasattr
(
self
,
"links"
):
json
[
"links"
]
=
self
.
links
res
[
"links"
]
=
self
.
links
if
hasattr
(
self
,
"mixins"
):
json
[
"mixins"
]
=
self
.
mixins
return
json
res
[
"mixins"
]
=
self
.
mixins
return
res
class
Link
(
Entity
):
...
...
@@ -190,18 +187,17 @@ class Link(Entity):
super
(
Link
,
self
)
.
__init__
(
*
args
,
**
kwargs
)
self
.
source
=
source
self
.
target
=
target
set_optional_attributes
(
self
,
self
.
link_optional_attributes
,
kwargs
)
set_optional_attributes
(
self
,
self
.
link_optional_attributes
,
kwargs
)
def
render_as_json
(
self
):
json
=
{
"kind"
:
self
.
kind
,
"id"
:
self
.
id
,
"source"
:
self
.
source
,
"target"
:
self
.
target
}
def
as_dict
(
self
):
res
=
{
"kind"
:
self
.
kind
,
"id"
:
self
.
id
,
"source"
:
self
.
source
,
"target"
:
self
.
target
}
if
hasattr
(
self
,
"mixins"
):
json
[
"mixins"
]
=
self
.
mixins
res
[
"mixins"
]
=
self
.
mixins
if
hasattr
(
self
,
"attributes"
):
json
[
"attributes"
]
=
self
.
attributes
res
[
"attributes"
]
=
self
.
attributes
if
hasattr
(
self
,
"actions"
):
json
[
"actions"
]
=
self
.
actions
res
[
"actions"
]
=
self
.
actions
if
hasattr
(
self
,
"title"
):
json
[
"title"
]
=
self
.
title
return
json
res
[
"title"
]
=
self
.
title
return
res
This diff is collapsed.
Click to expand it.
circle/occi/
occi_
infrastructure.py
→
circle/occi/infrastructure.py
View file @
89f43b4b
...
...
@@ -19,12 +19,13 @@
""" Implementation of the OCCI - Infrastructure extension classes """
from
occi
_
core
import
Resource
,
Link
from
occi
_
utils
import
action_list_for_resource
,
OcciActionInvocationError
from
occi
_
instances
import
(
COMPUTE_ACTIONS
,
LEASETIME_ACTIONS
,
from
occi
.
core
import
Resource
,
Link
from
occi
.
utils
import
action_list_for_resource
,
OcciActionInvocationError
from
occi
.
instances
import
(
COMPUTE_ACTIONS
,
LEASETIME_ACTIONS
,
STORAGE_ACTIONS
,
NETWORK_ACTIONS
)
from
common.models
import
HumanReadableException
from
celery.exceptions
import
TimeoutError
from
firewall.models
import
Rule
import
logging
...
...
@@ -117,11 +118,11 @@ class Compute(Resource):
for
disk
in
disks
:
storages
.
append
(
Storage
(
disk
))
for
storage
in
storages
:
links
.
append
(
StorageLink
(
self
,
storage
)
.
render_as_json
())
links
.
append
(
StorageLink
(
self
,
storage
)
.
as_dict
())
nics
=
[
NetworkInterface
(
self
,
Network
(
nic
.
vlan
))
for
nic
in
self
.
vm
.
interface_set
.
all
()]
for
networkinterface
in
nics
:
links
.
append
(
networkinterface
.
render_as_json
())
links
.
append
(
networkinterface
.
as_dict
())
return
links
def
invoke_action
(
self
,
user
,
action
,
attributes
):
...
...
@@ -137,6 +138,10 @@ class Compute(Resource):
self
.
save
(
user
,
attributes
)
elif
action
.
endswith
(
"renew"
):
self
.
renew
(
user
)
elif
action
.
endswith
(
"createstorage"
):
self
.
create_disk
(
user
,
attributes
)
elif
action
.
endswith
(
"downloadstorage"
):
self
.
download_disk
(
user
,
attributes
)
else
:
raise
OcciActionInvocationError
(
message
=
"Undefined action."
)
self
.
__init__
(
self
.
vm
)
...
...
@@ -147,6 +152,28 @@ class Compute(Resource):
except
HumanReadableException
as
e
:
raise
OcciActionInvocationError
(
message
=
e
.
get_user_text
())
def
create_disk
(
self
,
user
,
attributes
):
if
"size"
not
in
attributes
:
raise
OcciActionInvocationError
(
message
=
"Storage size is missing from action attributes!"
)
try
:
self
.
vm
.
create_disk
(
user
=
user
,
size
=
attributes
[
"size"
],
name
=
attributes
.
get
(
"name"
))
except
HumanReadableException
as
e
:
raise
OcciActionInvocationError
(
message
=
e
.
get_user_text
())
def
download_disk
(
self
,
user
,
attributes
):
if
"url"
not
in
attributes
:
raise
OcciActionInvocationError
(
message
=
"Storage image url is missing from action attributes!"
)
try
:
self
.
vm
.
download_disk
(
user
=
user
,
url
=
attributes
[
"url"
],
name
=
attributes
.
get
(
"name"
))
except
HumanReadableException
as
e
:
raise
OcciActionInvocationError
(
message
=
e
.
get_user_text
())
def
start
(
self
,
user
):
""" Start action on a compute instance """
try
:
...
...
@@ -371,9 +398,50 @@ class NetworkInterface(Link):
self
.
mixins
=
[
(
"http://schemas.ogf.org/occi/infrastructure/networkinterface#"
+
"ipnetworkinterface"
),
(
"http://circlecloud.org/occi/infrastructure/networkinterface#"
+
"ports"
),
]
self
.
attributes
=
self
.
set_attributes
()
def
invoke_action
(
self
,
user
,
action
,
attributes
):
if
action
.
endswith
(
"addport"
):
self
.
addport
(
user
,
attributes
)
elif
action
.
endswith
(
"removeport"
):
self
.
removeport
(
user
,
attributes
)
else
:
raise
OcciActionInvocationError
(
message
=
"Undefined action."
)
self
.
__init__
(
Compute
(
self
.
compute
.
vm
),
Network
(
self
.
network
.
vlan
))
def
addport
(
self
,
user
,
attributes
):
if
"port"
not
in
attributes
or
"protocol"
not
in
attributes
:
raise
OcciActionInvocationError
(
message
=
"Please supply the protocol and the port!"
)
try
:
self
.
compute
.
vm
.
add_port
(
user
=
user
,
host
=
self
.
interface
.
host
,
proto
=
attributes
[
"protocol"
],
port
=
int
(
attributes
[
"port"
]))
except
HumanReadableException
as
e
:
raise
OcciActionInvocationError
(
message
=
e
.
get_user_text
())
except
AttributeError
:
raise
OcciActionInvocationError
(
message
=
"Unmanaged interfaces cant add ports."
)
def
removeport
(
self
,
user
,
attributes
):
if
"port"
not
in
attributes
or
"protocol"
not
in
attributes
:
raise
OcciActionInvocationError
(
message
=
"Please supply the protocol and the port!"
)
try
:
rule
=
Rule
.
objects
.
filter
(
host
=
self
.
interface
.
host
)
.
filter
(
dport
=
attributes
[
"port"
])
.
get
(
proto
=
attributes
[
"protocol"
])
except
Rule
.
DoesNotExist
:
raise
OcciActionInvocationError
(
message
=
"Port does not exist!"
)
try
:
self
.
compute
.
vm
.
remove_port
(
user
=
user
,
rule
=
rule
)
except
HumanReadableException
as
e
:
raise
OcciActionInvocationError
(
message
=
e
.
get_user_text
())
def
set_attributes
(
self
):
attributes
=
{}
attributes
[
"occi.networkinterface.interface"
]
=
(
...
...
@@ -382,10 +450,17 @@ class NetworkInterface(Link):
attributes
[
"occi.networkinterface.state"
]
=
"active"
attributes
[
"occi.networkinterface.state.message"
]
=
(
"The networkinterface is active."
)
attributes
[
"occi.networkinterface.address"
]
=
(
unicode
(
self
.
interface
.
host
.
ipv4
))
if
self
.
interface
.
host
:
attributes
[
"occi.networkinterface.address"
]
=
(
unicode
(
self
.
interface
.
host
.
ipv4
))
attributes
[
"occi.networkinterface.gateway"
]
=
(
unicode
(
self
.
interface
.
vlan
.
network4
.
ip
))
attributes
[
"occi.networkinterface.allocation"
]
=
(
self
.
network
.
attributes
[
"occi.network.allocation"
])
attributes
[
"org.circlecloud.occi.networkinterface.ports"
]
=
(
self
.
get_open_ports
())
return
attributes
def
get_open_ports
(
self
):
return
[{
"port"
:
rule
.
dport
,
"protocol"
:
rule
.
proto
}
for
rule
in
Rule
.
objects
.
filter
(
host
=
self
.
interface
.
host
)]
This diff is collapsed.
Click to expand it.
circle/occi/
occi_
instances.py
→
circle/occi/instances.py
View file @
89f43b4b
...
...
@@ -19,7 +19,7 @@
""" Required instances of the OCCI classes """
from
vm.models.instance
import
InstanceTemplate
from
occi
_
core
import
Kind
,
Mixin
,
Attribute
,
Action
from
occi
.
core
import
Kind
,
Mixin
,
Attribute
,
Action
ENTITY_KIND
=
Kind
(
"http://schemas.ogf.org/occi/core#"
,
"entity"
,
...
...
@@ -237,6 +237,42 @@ CREDENTIALS_MIXIN = Mixin("http://circlecloud.org/occi/infrastructure/" +
applies
=
"http://schemas.ogf.org/occi/"
+
"infrastructure#compute"
)
NETWORKINTERFACE_PORTS_ATTRIBUTES
=
[
Attribute
(
"org.circlecloud.occi.networkinterface.ports"
,
"List"
,
False
,
False
,
description
=
"A list of open ports on the interface."
),
]
NETWORKINTERFACE_PORTS_ACTIONS
=
[
Action
(
"http://schemas.ogf.org/occi/infrastructure/networkinterface/action#"
,
"addport"
,
title
=
"Open a port on a network interface."
,
attributes
=
[
Attribute
(
"protocol"
,
"Enum {tcp, udp, icmp}"
,
True
,
False
),
Attribute
(
"port"
,
"Integer"
,
False
,
True
),
],
),
Action
(
"http://schemas.ogf.org/occi/infrastructure/networkinterface/action#"
,
"removeport"
,
title
=
"Closes a port on a network interface."
,
attributes
=
[
Attribute
(
"protocol"
,
"Enum {tcp, udp, icmp}"
,
True
,
False
),
Attribute
(
"port"
,
"Integer"
,
False
,
True
),
],
),
]
NETWORKINTERFACE_PORTS_MIXIN
=
Mixin
(
"http://circlecloud.org/occi/infrastructure/networkinterface#"
,
"ports"
,
title
=
"Network interface ports mixin"
,
attributes
=
NETWORKINTERFACE_PORTS_ATTRIBUTES
,
actions
=
NETWORKINTERFACE_PORTS_ACTIONS
,
applies
=
"http://schemas.ogf.org/occi/infrastructure#networkinterface"
,
)
LEASETIME_ATTRIBUTES
=
[
Attribute
(
"org.circlecloud.occi.leasetime.suspend"
,
"String"
,
False
,
False
,
description
=
"The time remaining until the compute "
+
...
...
@@ -264,11 +300,13 @@ OS_TPL_MIXIN = Mixin("http://schemas.ogf.org/occi/infrastructure#",
"os_tpl"
,
title
=
"OS Template"
)
ACTION_ARRAYS
=
[
COMPUTE_ACTIONS
,
NETWORK_ACTIONS
,
STORAGE_ACTIONS
,
LEASETIME_ACTIONS
,
NETWORKINTERFACE_PORTS_ACTIONS
,
]
...
...
@@ -290,10 +328,38 @@ def os_tpl_mixins(user):
templates
=
InstanceTemplate
.
get_objects_with_level
(
"user"
,
user
)
result
=
[]
for
template
in
templates
:
result
.
append
(
Mixin
(
"http://circlecloud.org/occi/templates/os#"
,
"os_template_"
+
str
(
template
.
pk
),
title
=
template
.
name
,
depends
=
(
OS_TPL_MIXIN
.
scheme
+
OS_TPL_MIXIN
.
term
)))
template_attrs
=
[
Attribute
(
"occi.compute.architecture"
,
"Enum {x86, x64}"
,
True
,
False
,
default
=
{
"x86_64"
:
"x64"
,
"x86-64 (64 bit)"
:
"x64"
,
"i686"
:
"x86"
,
"x86 (32 bit)"
:
"x86"
}[
template
.
arch
],
description
=
"CPU Architecture of the instance."
),
Attribute
(
"occi.compute.cores"
,
"Integer"
,
True
,
False
,
default
=
template
.
num_cores
,
description
=
"Number of virtual CPU cores assigned to "
+
"the instance."
),
Attribute
(
"occi.compute.share"
,
"Integer"
,
True
,
False
,
default
=
template
.
priority
,
description
=
"Relative number of CPU shares for the "
+
"instance."
),
Attribute
(
"occi.compute.memory"
,
"Float, 10^9 (GiB)"
,
True
,
False
,
default
=
template
.
ram_size
,
description
=
"Maximum RAM in gigabytes allocated to "
+
"the instance."
),
]
result
.
append
(
Mixin
(
"http://circlecloud.org/occi/templates/os#"
,
"os_template_"
+
str
(
template
.
pk
),
title
=
template
.
name
,
depends
=
(
OS_TPL_MIXIN
.
scheme
+
OS_TPL_MIXIN
.
term
),
attributes
=
template_attrs
,
)
)
return
result
...
...
@@ -304,6 +370,7 @@ def ALL_MIXINS(user):
CREDENTIALS_MIXIN
,
OS_TPL_MIXIN
,
LEASETIME_MIXIN
,
NETWORKINTERFACE_PORTS_MIXIN
,
]
template_mixins
=
os_tpl_mixins
(
user
)
for
template
in
template_mixins
:
...
...
This diff is collapsed.
Click to expand it.
circle/occi/migrations/__init__.py
deleted
100644 → 0
View file @
5a4b3e24
This diff is collapsed.
Click to expand it.
circle/occi/mixins.py
0 → 100644
View file @
89f43b4b
from
django.utils.decorators
import
method_decorator
from
django.views.decorators.csrf
import
ensure_csrf_cookie
from
occi.utils
import
OcciRequestNotValid
class
EnsureCsrfTokenMixin
(
object
):
@method_decorator
(
ensure_csrf_cookie
)
def
dispatch
(
self
,
*
args
,
**
kwargs
):
return
super
(
EnsureCsrfTokenMixin
,
self
)
.
dispatch
(
*
args
,
**
kwargs
)
class
OcciViewMixin
(
EnsureCsrfTokenMixin
):
def
dispatch
(
self
,
request
,
*
args
,
**
kwargs
):
if
not
request
.
user
.
is_authenticated
():
return
OcciRequestNotValid
(
message
=
"Authentication required."
,
status
=
403
)
.
response
return
super
(
OcciViewMixin
,
self
)
.
dispatch
(
request
,
*
args
,
**
kwargs
)
This diff is collapsed.
Click to expand it.
circle/occi/urls.py
View file @
89f43b4b
...
...
@@ -17,13 +17,18 @@
from
django.conf.urls
import
url
from
views
import
(
OcciLoginView
,
OcciLogoutView
,
OcciQueryInterfaceView
,
OcciComputeView
,
OcciComputeCollectionView
,
OcciStorageView
,
OcciStorageCollectionView
,
OcciNetworkView
,
OcciNetworkCollectionView
)
from
occi.views
import
(
OcciLoginView
,
OcciLogoutView
,
OcciQueryInterfaceView
,
OcciComputeView
,
OcciComputeCollectionView
,
OcciStorageView
,
OcciStorageCollectionView
,
OcciNetworkView
,
OcciNetworkCollectionView
,
OcciStoragelinkView
,
OcciStoragelinkCollectionView
,
OcciNetworkInterfaceView
,
OcciNetworkInterfaceCollectionView
,)
from
common.views
import
GenerateTokenView
urlpatterns
=
[
url
(
r'^login/token/$'
,
GenerateTokenView
.
as_view
()),
url
(
r'^login/$'
,
OcciLoginView
.
as_view
()),
url
(
r'^logout/$'
,
OcciLogoutView
.
as_view
()),
url
(
r'^-/$'
,
OcciQueryInterfaceView
.
as_view
()),
...
...
@@ -33,4 +38,11 @@ urlpatterns = [
url
(
r'^storage/(?P<id>\d+)/$'
,
OcciStorageView
.
as_view
()),
url
(
r'^network/$'
,
OcciNetworkCollectionView
.
as_view
()),
url
(
r'^network/(?P<id>\d+)/$'
,
OcciNetworkView
.
as_view
()),
url
(
r'^storagelink/$'
,
OcciStoragelinkCollectionView
.
as_view
()),
url
(
r'^storagelink/compute(?P<computeid>\d+)-storage(?P<storageid>\d+)/$'
,
OcciStoragelinkView
.
as_view
()),
url
(
r'^networkinterface/$'
,
OcciNetworkInterfaceCollectionView
.
as_view
()),
url
(
r'^networkinterface/compute(?P<computeid>\d+)-network(?P<networkid>'
+
r'\d+)/$'
,
OcciNetworkInterfaceView
.
as_view
()),
]
This diff is collapsed.
Click to expand it.
circle/occi/
occi_
utils.py
→
circle/occi/utils.py
View file @
89f43b4b
...
...
@@ -18,7 +18,7 @@
"""" Utilities for the OCCI implementation of CIRCLE """
from
django.http
import
Http
Response
from
django.http
import
Json
Response
import
json
...
...
@@ -89,44 +89,33 @@ def occi_response(data, *args, **kwargs):
by default. """
status
=
kwargs
.
get
(
"status"
,
200
)
# TODO: support for renderings other than json (e.g., text/plain)
data
=
json
.
dumps
(
data
)
response
=
HttpResponse
(
data
,
charset
=
"utf-8"
,
status
=
status
,
content_type
=
"application/json; charset=utf-8"
)
response
=
JsonResponse
(
data
,
status
=
status
)
# TODO: use Server header instead of OCCI-Server
response
[
"OCCI-Server"
]
=
"OCCI/1.2"
response
[
"Accept"
]
=
"application/json"
return
response
def
validate_request
(
request
,
authentication_required
=
True
,
has_data
=
False
,
**
kwargs
):
""" This function checks if the request's content type is
application/json and if the data is a valid json object. If the
authentication_required parameter is 'True', it will also check if
the user is authenticated. """
# checking if the user is authenticated
if
authentication_required
:
if
not
request
.
user
.
is_authenticated
():
raise
OcciRequestNotValid
(
"Authentication required."
,
status
=
403
)
if
has_data
:
# checking content type
if
request
.
META
.
get
(
"CONTENT_TYPE"
)
!=
"application/json"
:
raise
OcciRequestNotValid
(
"Only application/json content type"
+
" is allowed."
)
# checking if the data is a valid json
try
:
data
=
json
.
loads
(
request
.
body
.
decode
(
"utf-8"
))
except
KeyError
:
raise
OcciRequestNotValid
(
"The json provided in the request is "
+
"not valid."
)
# checking if provided keys are in the json
if
"data_keys"
in
kwargs
:
for
key
in
kwargs
[
"data_keys"
]:
if
key
not
in
data
:
raise
OcciRequestNotValid
(
key
+
" key is required."
)
# if validation was successful, the function returns the parsed
# json data
return
data
def
validate_request_data
(
request
,
data_keys
):
""" This function checks if all the required data keys are set and if the
input is a valid json object. """
# checking content type
if
request
.
META
.
get
(
"CONTENT_TYPE"
)
!=
"application/json"
:
raise
OcciRequestNotValid
(
"Only application/json content type"
+
" is allowed."
)
# checking if the data is a valid json
try
:
data
=
json
.
loads
(
request
.
body
.
decode
(
"utf-8"
))
except
KeyError
:
raise
OcciRequestNotValid
(
"The json provided in the request is "
+
"not valid."
)
# checking if provided keys are in the json
for
key
in
data_keys
:
if
key
not
in
data
:
raise
OcciRequestNotValid
(
key
+
" key is required."
)
# if validation was successful, the function returns the parsed
# json data
return
data
def
set_optional_attributes
(
self
,
optional_attributes
,
kwargs
):
...
...
This diff is collapsed.
Click to expand it.
circle/occi/views.py
View file @
89f43b4b
...
...
@@ -25,33 +25,33 @@ from django.views.generic import View
from
django.contrib.auth
import
logout
from
django.http
import
Http404
from
django.shortcuts
import
get_object_or_404
from
django.views.decorators.csrf
import
ensure_csrf_cookie
from
django.utils.decorators
import
method_decorator
from
vm.models.instance
import
Instance
,
InstanceTemplate
from
storage.models
import
Disk
from
firewall.models
import
Vlan
from
forms
import
OcciAuthForm
from
occi_infrastructure
import
Compute
,
Storage
,
Network
from
occi_utils
import
(
OcciResourceInstanceNotExist
,
from
occi.forms
import
OcciAuthForm
from
occi.infrastructure
import
(
Compute
,
Storage
,
Network
,
StorageLink
,
NetworkInterface
,)
from
occi.utils
import
(
OcciResourceInstanceNotExist
,
OcciActionInvocationError
,
OcciRequestNotValid
,
OcciResourceCreationError
,
OcciResourceDeletionError
,
occi_response
,
validate_request
)
from
occi
_
instances
import
ALL_KINDS
,
ALL_MIXINS
,
ALL_ACTIONS
validate_request
_data
)
from
occi
.
instances
import
ALL_KINDS
,
ALL_MIXINS
,
ALL_ACTIONS
from
common.models
import
HumanReadableException
from
occi.mixins
import
OcciViewMixin
,
EnsureCsrfTokenMixin
import
logging
log
=
logging
.
getLogger
(
__name__
)
class
OcciLoginView
(
View
):
class
OcciLoginView
(
EnsureCsrfTokenMixin
,
View
):
""" Authentication for the usage of the OCCI api.
This view responds with 200 and the access token in a Cookie if the
authentication succeeded, and with 400 if the provided username and
password is not valid. """
@method_decorator
(
ensure_csrf_cookie
)
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
""" Returns a response with a cookie to be used for requests other
than get. """
...
...
@@ -62,8 +62,6 @@ class OcciLoginView(View):
""" Returns a response with a cookie to be used for the OCCI api
requests. """
data
=
json
.
loads
(
request
.
body
.
decode
(
"utf-8"
))
log
.
error
(
data
)
print
(
data
)
form
=
OcciAuthForm
(
data
=
data
,
request
=
request
)
if
form
.
is_valid
():
result
=
{
"result"
:
"OK"
}
...
...
@@ -75,7 +73,7 @@ class OcciLoginView(View):
return
occi_response
(
result
,
status
=
400
)
class
OcciLogoutView
(
View
):
class
OcciLogoutView
(
EnsureCsrfTokenMixin
,
View
):
""" Logout """
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
...
...
@@ -84,21 +82,17 @@ class OcciLogoutView(View):
return
occi_response
(
result
)
class
OcciQueryInterfaceView
(
View
):
class
OcciQueryInterfaceView
(
OcciViewMixin
,
View
):
""" The view of the OCCI query interface """
@method_decorator
(
ensure_csrf_cookie
)
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
validate_request
(
request
)
except
OcciRequestNotValid
as
e
:
return
e
.
response
result
=
{
"kinds"
:
[],
"mixins"
:
[],
"actions"
:
[]}
for
kind
in
ALL_KINDS
():
result
[
"kinds"
]
.
append
(
kind
.
render_as_json
())
for
mixin
in
ALL_MIXINS
(
request
.
user
):
result
[
"mixins"
]
.
append
(
mixin
.
render_as_json
())
for
action
in
ALL_ACTIONS
():
result
[
"actions"
]
.
append
(
action
.
render_as_json
())
result
[
"kinds"
]
.
append
(
kind
.
as_dict
())
result
[
"mixins"
]
=
[
mixin
.
as_dict
()
for
mixin
in
ALL_MIXINS
(
request
.
user
)]
result
[
"actions"
]
=
[
action
.
as_dict
()
for
action
in
ALL_ACTIONS
()]
return
occi_response
(
result
)
def
post
(
self
,
request
,
*
args
,
**
kwargs
):
...
...
@@ -114,32 +108,20 @@ class OcciQueryInterfaceView(View):
"query interface."
},
status
=
400
)
class
OcciComputeCollectionView
(
View
):
@method_decorator
(
ensure_csrf_cookie
)
class
OcciComputeCollectionView
(
OcciViewMixin
,
View
):
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
validate_request
(
request
)
except
OcciRequestNotValid
as
e
:
return
e
.
response
vms
=
(
Instance
.
get_objects_with_level
(
"owner"
,
request
.
user
)
.
filter
(
destroyed_at
=
None
))
json
=
{
"resources"
:
[]}
for
vm
in
vms
:
json
[
"resources"
]
.
append
(
Compute
(
vm
)
.
render_as_json
())
return
occi_response
(
json
)
resources
=
[
Compute
(
vm
)
.
as_dict
()
for
vm
in
Instance
.
get_objects_with_level
(
"owner"
,
request
.
user
)
.
filter
(
destroyed_at
=
None
)]
return
occi_response
({
"resources"
:
resources
})
def
put
(
self
,
request
,
*
args
,
**
kwargs
):
# TODO: vm creation
return
occi_response
({
"message"
:
"TODO"
})
try
:
Instance
.
create_from_template
(
InstanceTemplate
.
objects
.
get
(
pk
=
1
),
request
.
user
)
except
Exception
:
return
occi_response
({
"test"
:
"tset"
})
return
occi_response
({})
class
OcciComputeView
(
View
):
class
OcciComputeView
(
OcciViewMixin
,
View
):
""" View of a compute instance """
def
get_vm_object
(
self
,
user
,
vmid
):
...
...
@@ -150,16 +132,12 @@ class OcciComputeView(View):
raise
OcciResourceInstanceNotExist
()
return
Compute
(
vm
)
@method_decorator
(
ensure_csrf_cookie
)
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
if
not
request
.
user
.
is_authenticated
():
return
occi_response
({
"error"
:
"Authentication required."
},
status
=
403
)
try
:
compute
=
self
.
get_vm_object
(
request
.
user
,
kwargs
[
"id"
])
except
OcciResourceInstanceNotExist
as
e
:
return
e
.
response
return
occi_response
(
compute
.
render_as_json
(),
charset
=
"utf-8"
)
return
occi_response
(
compute
.
as_dict
(),
charset
=
"utf-8"
)
def
post
(
self
,
request
,
*
args
,
**
kwargs
):
requestData
=
json
.
loads
(
request
.
body
.
decode
(
"utf-8"
))
...
...
@@ -174,7 +152,7 @@ class OcciComputeView(View):
requestData
.
get
(
"attributes"
,
None
))
except
OcciActionInvocationError
as
e
:
return
e
.
response
return
occi_response
(
compute
.
render_as_json
(),
status
=
200
)
return
occi_response
(
compute
.
as_dict
(),
status
=
200
)
elif
"attributes"
in
requestData
:
attrs
=
requestData
[
"attributes"
]
try
:
...
...
@@ -197,7 +175,7 @@ class OcciComputeView(View):
)
except
HumanReadableException
as
e
:
log
.
warning
(
e
.
get_user_text
())
return
occi_response
(
Compute
(
vm
)
.
render_as_json
(),
status
=
200
)
return
occi_response
(
Compute
(
vm
)
.
as_dict
(),
status
=
200
)
return
occi_response
({
"error"
:
"Bad request"
},
status
=
400
)
def
put
(
self
,
request
,
*
args
,
**
kwargs
):
...
...
@@ -208,8 +186,8 @@ class OcciComputeView(View):
# there has to be a mixins array in the provided rendering
data_keys
=
[
"mixins"
]
try
:
requestData
=
validate_request
(
request
,
True
,
True
,
data_keys
=
data_keys
)
requestData
=
validate_request
_data
(
request
,
data_keys
=
data_keys
)
except
OcciRequestNotValid
as
e
:
return
e
.
response
ostpl
=
"http://circlecloud.org/occi/templates/os#os_template_"
...
...
@@ -229,7 +207,7 @@ class OcciComputeView(View):
except
:
return
OcciResourceCreationError
()
.
response
compute
=
Compute
(
vm
)
return
occi_response
(
compute
.
render_as_json
())
return
occi_response
(
compute
.
as_dict
())
# TODO: update compute instance
return
occi_response
({
"error"
:
"Update of compute instances is "
+
"not implemented."
},
status
=
501
)
...
...
@@ -246,28 +224,23 @@ class OcciComputeView(View):
return
occi_response
({
"result"
:
"Compute instance deleted."
})
class
OcciStorageCollectionView
(
View
):
class
OcciStorageCollectionView
(
OcciViewMixin
,
View
):
@method_decorator
(
ensure_csrf_cookie
)
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
validate_request
(
request
)
except
OcciRequestNotValid
as
e
:
return
e
.
response
vms
=
(
Instance
.
get_objects_with_level
(
"owner"
,
request
.
user
)
.
filter
(
destroyed_at
=
None
))
json
=
{
"resources"
:
[]}
for
vm
in
vms
:
disks
=
vm
.
disks
.
all
()
for
disk
in
disks
:
json
[
"resources"
]
.
append
(
Storage
(
disk
)
.
render_as_json
())
json
[
"resources"
]
.
append
(
Storage
(
disk
)
.
as_dict
())
return
occi_response
(
json
)
def
put
(
self
,
request
,
*
args
,
**
kwargs
):
return
occi_response
({
"message"
:
"Not supported."
},
status
=
501
)
class
OcciStorageView
(
View
):
class
OcciStorageView
(
OcciViewMixin
,
View
):
""" View of a storage instance """
def
get_disk_object
(
self
,
user
,
diskid
):
...
...
@@ -283,17 +256,12 @@ class OcciStorageView(View):
return
Storage
(
disk
)
raise
OcciResourceInstanceNotExist
()
@method_decorator
(
ensure_csrf_cookie
)
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
validate_request
(
request
)
except
OcciRequestNotValid
as
e
:
return
e
.
response
try
:
disk
=
self
.
get_disk_object
(
request
.
user
,
kwargs
[
"id"
])
except
OcciResourceInstanceNotExist
as
e
:
return
e
.
response
return
occi_response
(
disk
.
render_as_json
(),
charset
=
"utf-8"
)
return
occi_response
(
disk
.
as_dict
(),
charset
=
"utf-8"
)
def
post
(
self
,
request
,
*
args
,
**
kwargs
):
requestData
=
json
.
loads
(
request
.
body
.
decode
(
"utf-8"
))
...
...
@@ -315,24 +283,26 @@ class OcciStorageView(View):
requestData
.
get
(
"attributes"
,
None
))
except
OcciActionInvocationError
as
e
:
return
e
.
response
return
occi_response
(
storage
.
render_as_json
(),
status
=
200
)
return
occi_response
(
storage
.
as_dict
(),
status
=
200
)
def
put
(
self
,
request
,
*
args
,
**
kwargs
):
return
OcciResourceCreationError
(
message
=
"Storage creation is not supported at this uri. "
+
"Please use the compute instances' actions!"
)
.
response
class
OcciNetworkCollectionView
(
OcciViewMixin
,
View
):
class
OcciNetworkCollectionView
(
View
):
@method_decorator
(
ensure_csrf_cookie
)
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
validate_request
(
request
)
except
OcciRequestNotValid
as
e
:
return
e
.
response
vlans
=
(
Vlan
.
get_objects_with_level
(
"owner"
,
request
.
user
))
json
=
{
"resources"
:
[]}
for
vlan
in
vlans
:
json
[
"resources"
]
.
append
(
Network
(
vlan
)
.
render_as_json
())
json
[
"resources"
]
.
append
(
Network
(
vlan
)
.
as_dict
())
return
occi_response
(
json
)
class
OcciNetworkView
(
View
):
class
OcciNetworkView
(
OcciViewMixin
,
View
):
""" View of a compute instance """
def
get_vlan_object
(
self
,
user
,
vlanid
):
...
...
@@ -343,17 +313,12 @@ class OcciNetworkView(View):
raise
OcciResourceInstanceNotExist
()
return
Network
(
vlan
)
@method_decorator
(
ensure_csrf_cookie
)
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
validate_request
(
request
)
except
OcciRequestNotValid
as
e
:
return
e
.
response
try
:
network
=
self
.
get_vlan_object
(
request
.
user
,
kwargs
[
"id"
])
except
OcciResourceInstanceNotExist
as
e
:
return
e
.
response
return
occi_response
(
network
.
render_as_json
(),
charset
=
"utf-8"
)
return
occi_response
(
network
.
as_dict
(),
charset
=
"utf-8"
)
def
post
(
self
,
request
,
*
args
,
**
kwargs
):
requestData
=
json
.
loads
(
request
.
body
.
decode
(
"utf-8"
))
...
...
@@ -375,4 +340,135 @@ class OcciNetworkView(View):
requestData
.
get
(
"attributes"
,
None
))
except
OcciActionInvocationError
as
e
:
return
e
.
response
return
occi_response
(
network
.
render_as_json
(),
status
=
200
)
return
occi_response
(
network
.
as_dict
(),
status
=
200
)
class
OcciStoragelinkCollectionView
(
OcciViewMixin
,
View
):
""" View of all storage link instances of the user """
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
vms
=
(
Instance
.
get_objects_with_level
(
"owner"
,
request
.
user
)
.
filter
(
destroyed_at
=
None
))
links
=
[
StorageLink
(
Compute
(
vm
),
Storage
(
disk
))
.
as_dict
()
for
vm
in
vms
for
disk
in
vm
.
disks
.
all
()]
return
occi_response
({
"links"
:
links
})
class
OcciStoragelinkView
(
OcciViewMixin
,
View
):
""" VIew of a storage link instance """
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
vm
=
get_object_or_404
(
Instance
.
get_objects_with_level
(
"owner"
,
request
.
user
)
.
filter
(
destroyed_at
=
None
),
pk
=
kwargs
[
"computeid"
])
except
Http404
:
return
OcciResourceInstanceNotExist
()
.
response
try
:
disk
=
vm
.
disks
.
get
(
pk
=
kwargs
[
"storageid"
])
except
Disk
.
DoesNotExist
:
return
OcciResourceInstanceNotExist
()
.
response
return
occi_response
(
StorageLink
(
Compute
(
vm
),
Storage
(
disk
))
.
as_dict
())
class
OcciNetworkInterfaceCollectionView
(
OcciViewMixin
,
View
):
""" View of network interface instances of a user """
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
vms
=
(
Instance
.
get_objects_with_level
(
"owner"
,
request
.
user
)
.
filter
(
destroyed_at
=
None
))
links
=
[
NetworkInterface
(
Compute
(
vm
),
Network
(
nwi
.
vlan
))
.
as_dict
()
for
vm
in
vms
for
nwi
in
vm
.
interface_set
.
all
()]
return
occi_response
({
"links"
:
links
})
class
OcciNetworkInterfaceView
(
OcciViewMixin
,
View
):
""" View of a network interface instance """
def
get_compute_object
(
self
,
user
,
vmid
):
try
:
vm
=
get_object_or_404
(
Instance
.
get_objects_with_level
(
"owner"
,
user
)
.
filter
(
destroyed_at
=
None
),
pk
=
vmid
)
except
Http404
:
raise
OcciResourceInstanceNotExist
()
return
Compute
(
vm
)
def
get_network_object
(
self
,
user
,
vlanid
):
try
:
vlan
=
get_object_or_404
(
Vlan
.
get_objects_with_level
(
"user"
,
user
),
pk
=
vlanid
)
except
Http404
:
raise
OcciResourceInstanceNotExist
()
return
Network
(
vlan
)
def
get_networkinterface_object
(
self
,
user
,
vmid
,
vlanid
):
compute
=
self
.
get_compute_object
(
user
,
vmid
)
try
:
interface
=
compute
.
vm
.
interface_set
.
get
(
vlan__pk
=
vlanid
)
except
:
raise
OcciResourceInstanceNotExist
()
return
NetworkInterface
(
compute
,
Network
(
interface
.
vlan
))
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
try
:
nic
=
self
.
get_networkinterface_object
(
request
.
user
,
kwargs
[
"computeid"
],
kwargs
[
"networkid"
])
except
OcciResourceInstanceNotExist
as
e
:
return
e
.
response
return
occi_response
(
nic
.
as_dict
())
def
post
(
self
,
request
,
*
args
,
**
kwargs
):
requestData
=
json
.
loads
(
request
.
body
.
decode
(
"utf-8"
))
if
"action"
in
requestData
:
try
:
nif
=
self
.
get_networkinterface_object
(
request
.
user
,
kwargs
[
"computeid"
],
kwargs
[
"networkid"
])
except
OcciResourceInstanceNotExist
as
e
:
return
e
.
response
try
:
nif
.
invoke_action
(
request
.
user
,
requestData
.
get
(
"action"
,
None
),
requestData
.
get
(
"attributes"
,
None
))
except
OcciActionInvocationError
as
e
:
return
e
.
response
return
occi_response
(
nif
.
as_dict
(),
status
=
200
)
return
OcciActionInvocationError
()
.
response
def
put
(
self
,
request
,
*
args
,
**
kwargs
):
compute
=
self
.
get_compute_object
(
request
.
user
,
kwargs
[
"computeid"
])
network
=
self
.
get_network_object
(
request
.
user
,
kwargs
[
"networkid"
])
try
:
compute
.
vm
.
add_interface
(
user
=
request
.
user
,
vlan
=
network
.
vlan
)
except
HumanReadableException
as
e
:
return
OcciResourceCreationError
(
message
=
e
.
get_user_text
())
.
response
except
Exception
as
e
:
return
OcciResourceCreationError
(
message
=
unicode
(
e
))
.
response
nif
=
NetworkInterface
(
compute
,
network
)
return
occi_response
(
nif
.
as_dict
())
def
delete
(
self
,
request
,
*
args
,
**
kwargs
):
compute
=
self
.
get_compute_object
(
request
.
user
,
kwargs
[
"computeid"
])
network
=
self
.
get_network_object
(
request
.
user
,
kwargs
[
"networkid"
])
try
:
interface
=
compute
.
vm
.
interface_set
.
get
(
vlan
=
network
.
vlan
)
except
:
return
OcciResourceInstanceNotExist
()
.
response
try
:
from
firewall.models
import
Host
from
vm.models.network
import
Interface
hc
=
Host
.
objects
.
filter
(
mac
=
interface
.
host
.
mac
)
.
count
()
ic
=
Interface
.
objects
.
filter
(
host__mac
=
interface
.
host
.
mac
)
.
count
()
compute
.
vm
.
remove_interface
(
user
=
request
.
user
,
interface
=
interface
)
except
HumanReadableException
as
e
:
return
OcciResourceDeletionError
(
message
=
e
.
get_user_text
())
.
response
except
Exception
:
from
firewall.models
import
Host
from
vm.models.network
import
Interface
hc
=
Host
.
objects
.
filter
(
mac
=
interface
.
host
.
mac
)
.
count
()
ic
=
Interface
.
objects
.
filter
(
host__mac
=
interface
.
host
.
mac
)
.
count
()
return
occi_response
({
"host"
:
hc
,
"interface"
:
ic
})
return
occi_response
({
"status"
:
"ok"
})
This diff is collapsed.
Click to expand it.
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment