Skip to content

Commit

Permalink
Merge branch 'last-modified' of 'https://github.com/sduenas/sortinghat'
Browse files Browse the repository at this point in the history
Merges #110
Closes #110
  • Loading branch information
sduenas committed Dec 20, 2017
2 parents bdad309 + 5e8bf01 commit e828440
Show file tree
Hide file tree
Showing 5 changed files with 444 additions and 4 deletions.
11 changes: 11 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,17 @@ After this initialize a new database:

## Compatibility between versions

SortingHat databases previous to 0.5.0.dev are no longer compatible. The
database schema changed in `uidentites` and `identities` tables to add the
field `last_modified` to log when a record was updated.

The next MySQL statements should be run to update the schema

```
mysql> ALTER TABLE uidentities ADD COLUMN last_modified DATETIME(6) DEFAULT NULL
mysql> ALTER TABLE identities ADD COLUMN last_modified DATETIME(6) DEFAULT NULL
```

SortingHat databases previous to 0.3.0 are no longer compatible. The
seed used to generate identities UUIDs changed and for that reason, these
ids should be re-generated.
Expand Down
2 changes: 1 addition & 1 deletion sortinghat/_version.py
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
# Versions compliant with PEP 440 https://www.python.org/dev/peps/pep-0440
__version__ = "0.4.6"
__version__ = "0.5.0.dev"
66 changes: 65 additions & 1 deletion sortinghat/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,8 @@
from __future__ import absolute_import
from __future__ import unicode_literals

import datetime

from . import utils
from .db.model import MIN_PERIOD_DATE, MAX_PERIOD_DATE,\
UniqueIdentity, Identity, Profile, Organization, Domain, Country, Enrollment,\
Expand Down Expand Up @@ -57,8 +59,11 @@ def add_unique_identity(db, uuid):
raise AlreadyExistsError(entity=uuid, uuid=uuid)

uidentity = UniqueIdentity(uuid=uuid)
session.add(uidentity)

last_modified = datetime.datetime.utcnow()
uidentity.last_modified = last_modified

session.add(uidentity)

def add_identity(db, source, email=None, name=None, username=None, uuid=None):
"""Add an identity to the registry.
Expand Down Expand Up @@ -156,6 +161,11 @@ def _find_unique_identity(session, uuid):
identity = Identity(id=identity_id, name=name, email=email,
username=username, source=source)
identity.uidentity = uidentity

last_modified = datetime.datetime.utcnow()
identity.last_modified = last_modified
uidentity.last_modified = last_modified

session.add(identity)

return identity_id
Expand Down Expand Up @@ -333,6 +343,10 @@ def add_enrollment(db, uuid, organization, from_date=None, to_date=None):

enrollment = Enrollment(uidentity=uidentity, organization=org,
start=from_date, end=to_date)

last_modified = datetime.datetime.utcnow()
uidentity.last_modified = last_modified

session.add(enrollment)


Expand Down Expand Up @@ -432,6 +446,9 @@ def edit_profile(db, uuid, **kwargs):
if 'email' in kwargs:
profile.email = to_none_if_empty(kwargs['email'])

last_modified = datetime.datetime.utcnow()
uidentity.last_modified = last_modified

session.add(profile)


Expand Down Expand Up @@ -487,6 +504,9 @@ def delete_identity(db, identity_id):
if not identity:
raise NotFoundError(entity=identity_id)

last_modified = datetime.datetime.utcnow()
identity.uidentity.last_modified = last_modified

session.delete(identity)


Expand Down Expand Up @@ -611,6 +631,9 @@ def delete_enrollment(db, uuid, organization, from_date=None, to_date=None):
for enr in enrollments:
session.delete(enr)

last_modified = datetime.datetime.utcnow()
identity.last_modified = last_modified


def delete_from_matching_blacklist(db, entity):
"""Remove an blacklisted entity from the registry.
Expand Down Expand Up @@ -695,9 +718,13 @@ def merge_unique_identities(db, from_uuid, to_uuid):
# Swap profiles
fuid.profile.uuid = to_uuid

last_modified = datetime.datetime.utcnow()
tuid.last_modified = last_modified

# Update identities
for identity in fuid.identities:
identity.uuid = to_uuid
identity.last_modified = last_modified

# Update and remove duplicated enrollments
for rol in fuid.enrollments:
Expand Down Expand Up @@ -805,6 +832,9 @@ def merge_enrollments(db, uuid, organization):
for enr in disjoint:
session.delete(enr)

last_modified = datetime.datetime.utcnow()
uidentity.last_modified = last_modified


def move_identity(db, from_id, to_uuid):
"""Move an identity to a unique identity.
Expand Down Expand Up @@ -848,7 +878,15 @@ def move_identity(db, from_id, to_uuid):
if fid.uuid == to_uuid:
return

fuid = session.query(UniqueIdentity).\
filter(UniqueIdentity.uuid == fid.uuid).first()

last_modified = datetime.datetime.utcnow()

fid.uuid = to_uuid
fuid.last_modified = last_modified
tuid.last_modified = last_modified
fid.last_modified = last_modified


def match_identities(db, uuid, matcher):
Expand Down Expand Up @@ -989,6 +1027,32 @@ def search_unique_identities(db, term, source=None):
return uidentities


def search_last_modified_identities(db, after):
"""Look for the uuids of identities modified on or after a given date.
This function returns the uuids of those unique identities and
identities that where modified on the given date or after it.
The result is a tuple containing two list of uuids: one with
unique identities and the other with identities.
:param db: database manater
:param after: look for identities modified on or after this date
:returns: a tuple containing the list of unique identities and the
identities modified
"""
with db.connect() as session:
query = session.query(UniqueIdentity).\
filter(UniqueIdentity.last_modified >= after)
uids = [uid.uuid for uid in query.order_by(UniqueIdentity.uuid).all()]

query = session.query(Identity).\
filter(Identity.last_modified >= after)
ids = [id_.id for id_ in query.order_by(Identity.id).all()]

return uids, ids


def registry(db, term=None):
"""List the organizations available in the registry.
Expand Down
7 changes: 7 additions & 0 deletions sortinghat/db/model.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@

from sqlalchemy import Column, Integer, String, DateTime,\
ForeignKey, UniqueConstraint
from sqlalchemy.dialects.mysql import DATETIME
from sqlalchemy.orm import backref, relationship
from sqlalchemy.ext.associationproxy import association_proxy
from sqlalchemy.ext.declarative import declarative_base
Expand Down Expand Up @@ -137,6 +138,9 @@ class UniqueIdentity(ModelBase):
__tablename__ = 'uidentities'

uuid = Column(String(128), primary_key=True)
last_modified = Column(DATETIME(fsp=6),
default=datetime.datetime.utcnow(),
onupdate=datetime.datetime.utcnow())

# One to one relationship
profile = relationship('Profile', backref='uidentities', uselist=False,
Expand Down Expand Up @@ -177,6 +181,9 @@ class Identity(ModelBase):
source = Column(String(32), nullable=False)
uuid = Column(String(128),
ForeignKey('uidentities.uuid', ondelete='CASCADE'))
last_modified = Column(DATETIME(fsp=6),
default=datetime.datetime.utcnow(),
onupdate=datetime.datetime.utcnow())

# Many-to-One relationship
uidentity = relationship('UniqueIdentity', backref='uuid_identy',
Expand Down
Loading

0 comments on commit e828440

Please sign in to comment.