Browse Source

More work towards filling out the client...

git-svn-id: https://bucket.mit.edu/svn/nilm/nilmdb@10624 ddd99763-3ecb-0310-9145-efcb8ce7c51f
tags/bxinterval-last
Jim Paris 12 years ago
parent
commit
a235c94c02
5 changed files with 58 additions and 61 deletions
  1. +1
    -1
      nilmdb/__init__.py
  2. +33
    -54
      nilmdb/client.py
  3. +1
    -1
      nilmdb/nilmdb.py
  4. +20
    -0
      nilmdb/server.py
  5. +3
    -5
      tests/test_client.py

+ 1
- 1
nilmdb/__init__.py View File

@@ -1,5 +1,5 @@
from nilmdb import NilmDB, StreamError from nilmdb import NilmDB, StreamError
from server import Server from server import Server
from client import Client, ClientError
from client import Client, ClientError, ServerError
from layout import * from layout import *
from serializer import WrapObject from serializer import WrapObject

+ 33
- 54
nilmdb/client.py View File

@@ -10,16 +10,30 @@ import re
import os import os
import json import json
import urlparse import urlparse
import urllib
import urllib2 import urllib2
from urllib2 import urlopen, HTTPError from urllib2 import urlopen, HTTPError
import pycurl import pycurl


class ClientError(Exception):
def __init__(self, code, message):
class NilmCommError(Exception):
"""Base exception for both ClientError and ServerError responses"""
def __init__(self, code, message, body = None):
Exception.__init__(self, message) Exception.__init__(self, message)
self.code = code self.code = code
self.body = body
def __str__(self): def __str__(self):
return sprintf("[%03d] %s", self.code, self.message) return sprintf("[%03d] %s", self.code, self.message)
def __repr__(self):
s = self.__str__()
if self.body:
s += "\n" + self.body
return s

class ClientError(NilmCommError):
pass

class ServerError(NilmCommError):
pass


class MyCurl(object): class MyCurl(object):
def __init__(self, baseurl = ""): def __init__(self, baseurl = ""):
@@ -37,6 +51,15 @@ class MyCurl(object):
url = urlparse.urljoin(url, "?" + urllib.urlencode(params, True)) url = urlparse.urljoin(url, "?" + urllib.urlencode(params, True))
self.curl.setopt(pycurl.URL, url) self.curl.setopt(pycurl.URL, url)
return url return url

def _check_error(self, body = None):
code = self.curl.getinfo(pycurl.RESPONSE_CODE)
if code >= 400 and code <= 499:
raise ClientError(code, "HTTP client error", body)
elif code >= 500 and code <= 599:
raise ServerError(code, "HTTP server error", body)
elif code != 200:
raise NilmCommError(code, "Unknown error", body)
def getjson(self, url, params = None): def getjson(self, url, params = None):
"""Simple GET that returns JSON string""" """Simple GET that returns JSON string"""
@@ -48,10 +71,8 @@ class MyCurl(object):
try: try:
self.curl.perform() self.curl.perform()
except pycurl.error as e: except pycurl.error as e:
raise ClientError(500, e[1])
code = self.curl.getinfo(pycurl.RESPONSE_CODE)
if code != 200:
raise ClientError(code, "HTTP error")
raise ServerError(500, e[1])
self._check_error(self._body)
return json.loads(self._body) return json.loads(self._body)


class Client(object): class Client(object):
@@ -81,59 +102,17 @@ class Client(object):
def stream_update_metadata(self): def stream_update_metadata(self):
raise NotImplementedError raise NotImplementedError


def stream_create(self):
raise NotImplementedError
def stream_create(self, path, layout, index = None):
params = { "path": path,
"layout" : layout }
if index is not None:
params["index"] = index
return self.curl.getjson("stream/create", params)


def stream_insert(self, path): def stream_insert(self, path):
params = { "path": path } params = { "path": path }
return self.curl.getjson("stream/insert", params) return self.curl.getjson("stream/insert", params)


# eq_(db.stream_list(), [])

# # Bad path
# with assert_raises(ValueError):
# db.stream_create("foo/bar/baz", "PrepData")
# with assert_raises(ValueError):
# db.stream_create("/foo", "PrepData")
# # Bad layout type
# with assert_raises(KeyError):
# db.stream_create("/newton/prep", "NoSuchLayout")
# # Bad index columns
# with assert_raises(KeyError):
# db.stream_create("/newton/prep", "PrepData", ["nonexistant"])
# db.stream_create("/newton/prep", "PrepData")
# db.stream_create("/newton/raw", "RawData")
# db.stream_create("/newton/zzz/rawnotch", "RawNotchedData")

# # Verify we got 3 streams
# eq_(db.stream_list(), [ ("/newton/prep", "PrepData"),
# ("/newton/raw", "RawData"),
# ("/newton/zzz/rawnotch", "RawNotchedData")
# ])
# # Match just one type
# eq_(db.stream_list(layout="RawData"), [ ("/newton/raw", "RawData") ])

# # Verify that columns were made right
# eq_(len(db.h5file.getNode("/newton/prep").cols), 9)
# eq_(len(db.h5file.getNode("/newton/raw").cols), 7)
# eq_(len(db.h5file.getNode("/newton/zzz/rawnotch").cols), 10)
# assert(db.h5file.getNode("/newton/prep").colindexed["timestamp"])
# assert(not db.h5file.getNode("/newton/prep").colindexed["p1"])

# # Set / get metadata
# eq_(db.stream_get_metadata("/newton/prep"), {})
# eq_(db.stream_get_metadata("/newton/raw"), {})
# meta1 = { "description": "The Data",
# "v_scale": "1.234" }
# meta2 = { "description": "The Data" }
# meta3 = { "v_scale": "1.234" }
# db.stream_set_metadata("/newton/prep", meta1)
# db.stream_update_metadata("/newton/prep", {})
# db.stream_update_metadata("/newton/raw", meta2)
# db.stream_update_metadata("/newton/raw", meta3)
# eq_(db.stream_get_metadata("/newton/prep"), meta1)
# eq_(db.stream_get_metadata("/newton/raw"), meta1)



# streams = getjson("/stream/list") # streams = getjson("/stream/list")




+ 1
- 1
nilmdb/nilmdb.py View File

@@ -181,7 +181,7 @@ class NilmDB(object):
if index is None and "timestamp" in table.colnames: if index is None and "timestamp" in table.colnames:
index = [ "timestamp" ] index = [ "timestamp" ]
for ind in index: for ind in index:
table.cols._f_col(ind).createIndex()
table.cols._f_col(str(ind)).createIndex()
except KeyError as e: except KeyError as e:
# Remove this table if we got an error # Remove this table if we got an error
self.h5file.removeNode(group, node) self.h5file.removeNode(group, node)


+ 20
- 0
nilmdb/server.py View File

@@ -67,6 +67,26 @@ class Stream(NilmApp):
or layout""" or layout"""
return self.db.stream_list(path, layout) return self.db.stream_list(path, layout)


# /stream/create?path=/newton/prep&layout=PrepData
@cherrypy.expose
@cherrypy.tools.json_out()
def create(self, path, layout, index = None):
"""Create a new stream in the database. Provide path
and one of the nilmdb.layout.layouts keys.

index: layout columns listed here are marked as PyTables indices.
If index = none, the 'timestamp' column is indexed if it exists.
Pass an empty list to prevent indexing.
"""
try:
return self.db.stream_create(path, layout, index)
except ValueError as e:
raise cherrypy.HTTPError("400 Bad Request",
"ValueError: " + e.message)
except KeyError as e:
raise cherrypy.HTTPError("400 Bad Request",
"KeyError: " + e.message)

# /stream/get_metadata?path=/newton/prep # /stream/get_metadata?path=/newton/prep
# /stream/get_metadata?path=/newton/prep?key=foo&key=bar # /stream/get_metadata?path=/newton/prep?key=foo&key=bar
@cherrypy.expose @cherrypy.expose


+ 3
- 5
tests/test_client.py View File

@@ -1,7 +1,7 @@
import nilmdb import nilmdb
from nilmdb.printf import * from nilmdb.printf import *


from nilmdb.client import ClientError
from nilmdb.client import ClientError, ServerError


from nose.tools import * from nose.tools import *
from nose.tools import assert_raises from nose.tools import assert_raises
@@ -51,15 +51,13 @@ class TestClient(object):
def test_client_basic(self): def test_client_basic(self):
# Test a fake host # Test a fake host
client = nilmdb.Client(url = "http://localhost:1/") client = nilmdb.Client(url = "http://localhost:1/")
with assert_raises(nilmdb.ClientError) as e:
with assert_raises(nilmdb.ServerError):
client.version() client.version()
eq_(e.exception.code, 500)


# Then a fake URL on a real host # Then a fake URL on a real host
client = nilmdb.Client(url = "http://localhost:12380/fake/") client = nilmdb.Client(url = "http://localhost:12380/fake/")
with assert_raises(nilmdb.ClientError) as e:
with assert_raises(nilmdb.ClientError):
client.version() client.version()
eq_(e.exception.code, 404)


# Now use the real URL # Now use the real URL
client = nilmdb.Client(url = "http://localhost:12380/") client = nilmdb.Client(url = "http://localhost:12380/")


Loading…
Cancel
Save