aboutsummaryrefslogtreecommitdiff
path: root/rpki
diff options
context:
space:
mode:
authorRob Austein <sra@hactrn.net>2016-01-08 15:30:47 +0000
committerRob Austein <sra@hactrn.net>2016-01-08 15:30:47 +0000
commit1683d8fb0fa58162d15b2877fba477e505340545 (patch)
treef79f1f140322260f0c309e184809e7658261ab0e /rpki
parent327638bdc5114c96171827764690d0434872fa8b (diff)
Start converting rcynicng to use a database.
svn path=/branches/tk705/; revision=6218
Diffstat (limited to 'rpki')
-rw-r--r--rpki/POW/__init__.py4
-rw-r--r--rpki/django_settings/common.py5
-rw-r--r--rpki/django_settings/rcynic.py61
-rw-r--r--rpki/rcynicdb/__init__.py0
-rw-r--r--rpki/rcynicdb/models.py78
5 files changed, 147 insertions, 1 deletions
diff --git a/rpki/POW/__init__.py b/rpki/POW/__init__.py
index e88fae80..b6f15a39 100644
--- a/rpki/POW/__init__.py
+++ b/rpki/POW/__init__.py
@@ -164,6 +164,7 @@ validation_status = StatusCodeDB(
TRUST_ANCHOR_WITH_CRLDP = "Trust anchor can't have CRLDP",
UNKNOWN_AFI = "Unknown AFI",
UNKNOWN_OPENSSL_VERIFY_ERROR = "Unknown OpenSSL verify error",
+ UNREADABLE_OBJECT = "Unreadable object",
UNREADABLE_TRUST_ANCHOR = "Unreadable trust anchor",
UNREADABLE_TRUST_ANCHOR_LOCATOR = "Unreadable trust anchor locator",
WRONG_OBJECT_VERSION = "Wrong object version",
@@ -181,7 +182,8 @@ validation_status = StatusCodeDB(
DIGEST_MISMATCH = "Digest mismatch",
EE_CERTIFICATE_WITH_1024_BIT_KEY = "EE certificate with 1024 bit key",
GRATUITOUSLY_CRITICAL_EXTENSION = "Gratuitously critical extension",
- ISSUER_USES_MULTIPLE_CRLDP_VALUES = "Issuer uses multiple CRLDP values",\
+ INAPPROPRIATE_OBJECT_TYPE_SKIPPED = "Inappropriate object type skipped",
+ ISSUER_USES_MULTIPLE_CRLDP_VALUES = "Issuer uses multiple CRLDP values",
MULTIPLE_RSYNC_URIS_IN_EXTENSION = "Multiple rsync URIs in extension",
NONCONFORMANT_ISSUER_NAME = "Nonconformant X.509 issuer name",
NONCONFORMANT_SUBJECT_NAME = "Nonconformant X.509 subject name",
diff --git a/rpki/django_settings/common.py b/rpki/django_settings/common.py
index 4aa3e119..2f41fe77 100644
--- a/rpki/django_settings/common.py
+++ b/rpki/django_settings/common.py
@@ -118,3 +118,8 @@ if cfg.has_option("secret-key", section = "web_portal"):
SECRET_KEY = cfg.get("secret-key", section = "web_portal")
else:
SECRET_KEY = os.urandom(66).encode("hex")
+
+
+# Django defaults to thinking everybody lives in Chicago.
+
+TIME_ZONE = "UTC"
diff --git a/rpki/django_settings/rcynic.py b/rpki/django_settings/rcynic.py
new file mode 100644
index 00000000..90491ddc
--- /dev/null
+++ b/rpki/django_settings/rcynic.py
@@ -0,0 +1,61 @@
+# $Id$
+
+# Copyright (C) 2014 Dragon Research Labs ("DRL")
+#
+# Permission to use, copy, modify, and distribute this software for any
+# purpose with or without fee is hereby granted, provided that the above
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND DRL DISCLAIMS ALL WARRANTIES WITH
+# REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+# AND FITNESS. IN NO EVENT SHALL DRL BE LIABLE FOR ANY SPECIAL, DIRECT,
+# INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
+# LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
+# OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+# PERFORMANCE OF THIS SOFTWARE.
+
+"""
+This module contains configuration settings for Django libraries.
+At present, rcynicng only uses the Django ORM, not the rest of Django.
+Unlike the CA tools rcynicng defaults to using SQLite3 as its database
+engine, so we tweak the defaults a little before instantiating the
+database configuration here.
+"""
+
+from .common import * # pylint: disable=W0401,W0614
+
+__version__ = "$Id$"
+
+
+# Database configuration.
+
+class DBConfigurator(DatabaseConfigurator):
+
+ default_sql_engine = "sqlite3"
+
+ @property
+ def sqlite3(self):
+ return dict(
+ ENGINE = "django.db.backends.sqlite3",
+ NAME = cfg.get("sql-database", section = self.section, default = "rcynic.db"))
+
+
+DATABASES = DBConfigurator().configure(cfg, "rcynic")
+
+del DBConfigurator
+del DatabaseConfigurator
+
+
+# Apps.
+
+INSTALLED_APPS = ["rpki.rcynicdb"]
+
+
+# Allow local site to override any setting above -- but if there's
+# anything that local sites routinely need to modify, please consider
+# putting that configuration into rpki.conf and just adding code here
+# to read that configuration.
+try:
+ from local_settings import * # pylint: disable=W0401,F0401
+except ImportError:
+ pass
diff --git a/rpki/rcynicdb/__init__.py b/rpki/rcynicdb/__init__.py
new file mode 100644
index 00000000..e69de29b
--- /dev/null
+++ b/rpki/rcynicdb/__init__.py
diff --git a/rpki/rcynicdb/models.py b/rpki/rcynicdb/models.py
new file mode 100644
index 00000000..318f87e3
--- /dev/null
+++ b/rpki/rcynicdb/models.py
@@ -0,0 +1,78 @@
+# First cut at ORM models for rcynicng, assuming for now that we're
+# going to go with Django rather than raw SQL.
+
+from django.db import models
+
+# HTTP/HTTPS/RSYNC fetch event.
+#
+# Open issue: for RRDP, are we just recording the notification fetch,
+# or the snapshot/delta fetches as well? If the latter, to which
+# retrieval event does the RRDPSnapshot 1:1 relationship refer? For
+# that matter, should we somehow be recording the relationship between
+# the notification and snapshot/delta fetches? Given that, at least
+# in the current protocol, we will only do either one snapshot fetch
+# or one delta fetch after the notify fetch, we could just use two
+# URIs in the retrieval record, if we allow the second to be empty
+# (which we would have to do anyway for rsync).
+#
+# Or we could add some kind of fun SQL self-reference, which, in
+# Django, looks like:
+#
+# models.ForeignKey('self', on_delete = models.CASCADE)
+#
+# except that it's more like a 1:1 recursive relationship, which isn't
+# mentioned in the Django docs, but which supposedly
+# (http://stackoverflow.com/questions/18271001/django-recursive-relationship)
+# works the same way:
+#
+# models.OneToOneField('self', null = True)
+#
+# Unclear whether we still need "on_delete = models.CASCADE", probably.
+# Example on StackOverflow has a complex .save() method, but that may
+# be specific to the original poster's desired semantics.
+
+class Retrieval(models.Model):
+ uri = models.TextField()
+ started = models.DateTimeField()
+ finished = models.DateTimeField()
+ successful = models.BooleanField()
+
+# Collection of validated objects (like current
+# rsync-data/authenticated.yyyy-mm-ddTHH:MM:SS/ tree)
+
+class Authenticated(models.Model):
+ timestamp = models.DateTimeField()
+
+# One instance of an RRDP snapshot.
+#
+# Deltas are processed by finding the RRDPSnapshot holding the
+# starting point, creating a new RRDPSnapshot for the endpoint, and
+# applying all necessary deltas (with consistency checks all along the
+# way) to get from one to the other; we don't commit the endpoint (or
+# anything created during the process) until and unless it all works.
+#
+# Not sure we want uuid field, drop if not useful.
+
+class RRDPSnapshot(models.Model):
+ timestamp = models.DateTimeField()
+ uuid = models.UUIDField()
+ serial = models.BigIntegerField()
+ retrieved = models.OneToOneField(Retrieval)
+
+# RPKI objects.
+
+class RPKIObject(models.Model):
+ der = models.BinaryField(unique = True)
+ uri = models.TextField()
+ aki = models.SlugField(max_length = 40) # hex SHA-1
+ ski = models.SlugField(max_length = 40) # hex SHA-1
+ hash = models.SlugField(max_length = 64) # hex SHA-256
+ retrieved = models.ForeignKey(Retrieval)
+ authenticated = models.ManyToManyField(Authenticated)
+ snapshot = models.ManyToManyField(RRDPSnapshot)
+
+# No exact analogue to current unauthenticated tree. Generally, when
+# we would have looked in the unauthenticated tree we want the most
+# recently retrieved copy of a particular object, but particular
+# object gets a little weird in RRDP universe. See Tim's draft, not
+# gospel but best worked example available to date.