Contact: fumanchu@aminus.org

Log in as guest/dejavu to create tickets

I think I've seen this ORM somewhere before...

Changeset 427

Show
Ignore:
Timestamp:
03/26/07 03:46:02
Author:
fumanchu
Message:

Updates in sync with Geniusql 53 (moved codewalk and logic there).

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/__init__.py

    r426 r427  
    4444from dejavu.schemas import * 
    4545from dejavu.units import * 
    46 from dejavu import logic 
     46 
     47from geniusql import logic 
     48from geniusql import logicfuncs 
    4749 
    4850 
     
    5052# process. Otherwise, you should create your own instance per application. 
    5153dejavuarena = Arena() 
    52  
    53  
    54 ########################################################################### 
    55 ##                                                                       ## 
    56 ##                           Logic functions                             ## 
    57 ##                                                                       ## 
    58 ########################################################################### 
    59  
    60  
    61 def icontains(a, b): 
    62     """Case-insensitive test b in a. Note the operand order.""" 
    63     return icontainedby(b, a) 
    64  
    65 def icontainedby(a, b): 
    66     """Case-insensitive test a in b. Note the operand order.""" 
    67     if isinstance(b, basestring): 
    68         # Looking for text in a string. 
    69         if a is None or b is None: 
    70             return False 
    71         return a.lower() in b.lower() 
    72     else: 
    73         # Looking for field in (a, b, c). 
    74         # Force all args to lowercase for case-insensitive comparison. 
    75         if a is None or not b: 
    76             return False 
    77         return a.lower() in [x.lower() for x in b] 
    78  
    79 def istartswith(a, b): 
    80     """True if a starts with b (case-insensitive), False otherwise.""" 
    81     if a is None or b is None: 
    82         return False 
    83     return a.lower().startswith(b.lower()) 
    84  
    85 def iendswith(a, b): 
    86     """True if a ends with b (case-insensitive), False otherwise.""" 
    87     if a is None or b is None: 
    88         return False 
    89     return a.lower().endswith(b.lower()) 
    90  
    91 def ieq(a, b): 
    92     """True if a == b (case-insensitive), False otherwise.""" 
    93     if a is None or b is None: 
    94         return False 
    95     return (a.lower() == b.lower()) 
    96  
    97 def year(value): 
    98     """The year attribute of a date.""" 
    99     if isinstance(value, (_datetime.date, _datetime.datetime)): 
    100         return value.year 
    101     else: 
    102         return None 
    103  
    104 def month(value): 
    105     """The month attribute of a date.""" 
    106     if isinstance(value, (_datetime.date, _datetime.datetime)): 
    107         return value.month 
    108     else: 
    109         return None 
    110  
    111 def day(value): 
    112     """The day attribute of a date.""" 
    113     if isinstance(value, (_datetime.date, _datetime.datetime)): 
    114         return value.day 
    115     else: 
    116         return None 
    117  
    118 def now(): 
    119     """Late-bound datetime.datetime.now(). Taint this when early binding.""" 
    120     return _datetime.datetime.now() 
    121 now.bind_late = True 
    122  
    123 def today(): 
    124     """Late-bound datetime.date.today(). Taint this when early binding.""" 
    125     return _datetime.date.today() 
    126 today.bind_late = True 
    127  
    128 def iscurrentweek(value): 
    129     """If value is in the current week, return True, else False.""" 
    130     if isinstance(value, (_datetime.date, _datetime.datetime)): 
    131         return _datetime.date.today().strftime('%W%Y') == value.strftime('%W%Y') 
    132     else: 
    133         return False 
    134 iscurrentweek.bind_late = True 
    135  
    136 # Inject these functions into the logic module's globals. 
    137 class _Empty(object): pass 
    138 _d = _Empty() 
    139 for _name in ['icontains', 'icontainedby', 'istartswith', 'iendswith', 
    140               'ieq', 'year', 'month', 'now', 'today', 'iscurrentweek']: 
    141     setattr(_d, _name, globals()[_name]) 
    142 logic.dejavu = _d 
    143 del _name, _d, _Empty 
  • trunk/arenas.py

    r426 r427  
    99 
    1010from dejavu.containers import Graph 
    11 from dejavu import logic, errors, storage, xray 
     11from dejavu import errors, storage, xray 
     12from geniusql import logic 
    1213 
    1314__all__ = ['Arena', 'Sandbox', 'logflags', 
  • trunk/engines.py

    r426 r427  
    1515 
    1616import dejavu 
    17 from dejavu import errors, logic, recur 
     17from dejavu import errors, recur 
     18from geniusql import logic 
    1819 
    1920 
  • trunk/storage/__init__.py

    r426 r427  
    1010import warnings 
    1111 
    12 from dejavu import errors, logic, recur 
     12from dejavu import errors, recur 
     13from geniusql import logic 
    1314 
    1415 
  • trunk/storage/db.py

    r426 r427  
    3434 
    3535import geniusql 
     36from geniusql import logic 
    3637 
    3738import dejavu 
    38 from dejavu import logic, storage, logflags, xray 
     39from dejavu import storage, logflags, xray 
    3940from dejavu.errors import StorageWarning, MappingError 
    4041 
  • trunk/storage/storefs.py

    r426 r427  
    99 
    1010import dejavu 
    11 from dejavu import errors, logic, storage 
     11from dejavu import errors, storage 
     12 
     13from geniusql import logic 
    1214 
    1315 
  • trunk/storage/storeram.py

    r426 r427  
    66import thread 
    77 
    8 from dejavu import logic, UnitJoin 
     8from dejavu import UnitJoin 
    99from dejavu.storage import StorageManager 
     10from geniusql import logic 
    1011 
    1112 
  • trunk/storage/storeshelve.py

    r426 r427  
    1616 
    1717import dejavu 
    18 from dejavu import errors, logic, storage 
     18from dejavu import errors, storage 
     19from geniusql import logic 
    1920 
    2021 
  • trunk/test/clinic_fixture.py

    r426 r427  
    22 
    33import datetime 
     4dt = datetime.datetime 
     5td = datetime.timedelta 
    46import os 
    57thisdir = os.path.dirname(__file__) 
     
    2325class Argument(Unit): 
    2426    Topic = UnitProperty() 
    25     Start = UnitProperty(datetime.datetime
     27    Start = UnitProperty(dt
    2628    Duration = UnitProperty(datetime.timedelta) 
    2729    ClinicID = UnitProperty(int, index=True) 
     
    6466         
    6567        # Arguments 
    66         sixtynine = datetime.datetime(1969, 1, 1) 
    67         td = datetime.timedelta 
     68        sixtynine = dt(1969, 1, 1) 
    6869        for s in range(5): 
    6970            for d in range(12): 
     
    7475                              ) 
    7576                box.memorize(arg) 
    76                 box.memorize(Participant(ParticipantID=brown.ID, ArgumentID=arg.ID)) 
    77                 box.memorize(Participant(ParticipantID=green.ID, ArgumentID=arg.ID)) 
     77                box.memorize(Participant(DirectoryID=brown.ID, ArgumentID=arg.ID)) 
     78                if d % 2: 
     79                    box.memorize(Participant(DirectoryID=green.ID, ArgumentID=arg.ID)) 
     80                else: 
     81                    box.memorize(Participant(DirectoryID=white.ID, ArgumentID=arg.ID)) 
    7882        box.flush_all() 
    7983     
    8084    def test_2_simple_views(self): 
    8185        # Get the start and duration times for: "What is an Argument?" 
    82         sixtynine = datetime.datetime(1969, 1, 1) 
    83         td = datetime.timedelta 
     86        sixtynine = dt(1969, 1, 1) 
    8487        expected = [] 
    8588        for s in range(5): 
     
    104107        self.assertEqual(actual, expected) 
    105108     
    106 ##    def test_3_multidim_views(self): 
    107 ##        source = Clinic << Argument << Participant 
    108 ##        sources[Clinic] = ['ID', 'Name'] 
    109 ##        brownargs = views.View(Source=Argument, 
    110 ##                               Filter=lambda x: x.DirectoryID == brown.ID) 
    111 ##        self.assertEqual(brownargs(), []) 
    112  
     109    def test_3_multidim_views(self): 
     110        box = arena.new_sandbox() 
     111        brownid = box.unit(Directory, Name='Sam Brown').ID 
     112        box.flush_all() 
     113         
     114        brownargs = views.View(Clinic << Argument << Participant, 
     115                               [['ID', 'Name'], None, None], 
     116                               lambda c, a, p: p.DirectoryID == brownid) 
     117        clsname = 'BrownClinics' 
     118        snap = brownargs.results(clsname, arena) 
     119        snapclass = snap.unitclass(arena) 
     120        self.assertEqual(snapclass.__name__, clsname) 
     121        actual = list(arena.view(snapclass, ['Name'])) 
     122        actual.sort() 
     123        self.assertEqual(actual, [(u'The Argument Clinic',)] * 60) 
     124     
     125    def test_4_aggregate_views(self): 
     126        firstargs = views.View(Argument << Participant << Directory, 
     127                               lambda a, p, d: [d.Name, min(a.Start)] 
     128                               ) 
     129        clsname = 'FirstArgument' 
     130        snap = firstargs.results(clsname, arena) 
     131        snapclass = snap.unitclass(arena) 
     132        self.assertEqual(snapclass.__name__, clsname) 
     133        actual = list(arena.view(snapclass)) 
     134        actual.sort() 
     135        self.assertEqual(actual, [(u'Alice White', dt(1969, 1, 31)), 
     136                                  (u'David Green', dt(1969, 1, 1)), 
     137                                  (u'Sam Brown', dt(1969, 1, 1)), 
     138                                  ]) 
    113139 
    114140 
     
    119145    if isinstance(message, unicode): 
    120146        message = message.encode('utf8') 
    121     s = "%s %s" % (datetime.datetime.now().isoformat(), message) 
     147    s = "%s %s" % (dt.now().isoformat(), message) 
    122148    f = open(logname, 'ab') 
    123149    f.write(s + '\n') 
     
    140166     
    141167    try: 
    142         sm.db.typeadapter.add_pickled_type(views.Sources) 
    143         sm.db.adaptertosql.add_pickled_type(views.Sources) 
    144         sm.db.adapterfromdb.add_pickled_type(views.Sources) 
     168        for cls in (views.ViewSource, views.ViewAttrs): 
     169            sm.db.typeadapter.add_pickled_type(cls) 
     170            sm.db.adaptertosql.add_pickled_type(cls) 
     171            sm.db.adapterfromdb.add_pickled_type(cls) 
    145172    except AttributeError: 
    146173        pass 
     
    169196            # Run the OLAPTests and time it. 
    170197            case = loader(OLAPTests) 
    171             startTime = datetime.datetime.now() 
     198            startTime = dt.now() 
    172199            tools.djvTestRunner.run(case) 
    173             print "Ran clinic case in:", datetime.datetime.now() - startTime 
     200            print "Ran clinic case in:", dt.now() - startTime 
    174201        except: 
    175202            traceback.print_exc() 
  • trunk/test/test.py

    r426 r427  
    8888    testList = [ 
    8989        'test_analysis', 
    90         'test_codewalk', 
    9190        'test_containers', 
    9291        'test_dejavu', 
    93         'test_logic', 
    9492        'test_storeram', 
    9593        'test_storeburned', 
  • trunk/test/test_storemsaccess.py

    r426 r427  
    1717    else: 
    1818         
    19         class CurrencyAdapter(ado.TypeAdapter_MSAccess): 
    20             """Stores Decimal and FixedPoint objects as CURRENCY.""" 
    21              
    22             def decimal_type(self, colname, precision, scale): 
    23                 if precision == 0: 
    24                     precision = 19 
    25                 if scale > precision: 
    26                     scale = precision 
    27                 if scale > 4 or precision - scale > 15: 
    28                     return "TEXT" 
    29                 return "CURRENCY" 
    30              
    3119        SM_class = "access" 
    3220        opts = {'connections.Connect': 
     
    3725            import zoo_fixture 
    3826             
    39             # lists to keep track of the test_currency runs 
    40             standard_runs = [] 
    41             altered_runs = [] 
    42              
    43             def test_currency(obj): 
    44                 sm = zoo_fixture.arena.stores['testSM'] 
    45                 fta = sm.db.typeadapter.__class__.__name__ 
    46                  
    47                 for c, p in [('Exhibit', 'Acreage'), ('Zoo', 'Admission')]: 
    48                     dbtype = sm.schema[c][p].dbtype 
    49                     if fta == "CurrencyAdapter": 
    50                         if dbtype != "CURRENCY" and not dbtype.startswith("WCHAR"): 
    51                             obj.fail("%s wrong type for %s.%s" % (dbtype, c, p)) 
    52                     else: 
    53                         if not dbtype.startswith("NUMERIC") and not dbtype.startswith("WCHAR"): 
    54                             obj.fail("%s wrong type for %s.%s" % (dbtype, c, p)) 
    55                         obj.assertEqual(len(standard_runs), 0) 
    56              
    5727            # Isolate schema changes from one test to the next. 
    5828            reload(zoo_fixture) 
    5929             
    60             # test the standard MS Access setup where Decimal and FixedPoint 
    61             # objects are stored in the database as INTEGERS, LONGS or NUMERIC 
    62             print 
    63             print "Standard MSAccess test." 
    64             zoo_fixture.ZooTests.test_currency = test_currency 
    6530            zoo_fixture.init() 
    6631            zoo_fixture.run(SM_class, opts) 
    67             standard_runs.append(True) 
    68              
    69             # plugin the adapter for testing CURRENCY columns 
    70             ado.MSAccessDatabase.typeadapter = CurrencyAdapter() 
    71              
    72             reload(zoo_fixture) 
    73              
    74             # test storing and recalling Decimal values to the database using 
    75             # CURRENCY columns - the (current) default behavior of pythoncom 
    76             # is to return CURRENCY values as a tuple 
    77             print 
    78             print "MSAccess test - CURRENCY returned as tuple." 
    79             zoo_fixture.ZooTests.test_currency = test_currency 
    80             zoo_fixture.init() 
    81             zoo_fixture.run(SM_class, opts) 
    82             altered_runs.append(True) 
    83              
    84             # set pythoncom to return CURRENCY values as Decimal objects 
    85             pythoncom.__future_currency__ = True 
    86              
    87             reload(zoo_fixture) 
    88              
    89             # test storing and recalling Decimal values to the database using 
    90             # CURRENCY columns - CURRENCY values are now returned as Decimal 
    91             # objects 
    92             print 
    93             print "MSAccess test - CURRENCY returned as Decimal." 
    94             zoo_fixture.ZooTests.test_currency = test_currency 
    95             zoo_fixture.init() 
    96             zoo_fixture.run(SM_class, opts) 
    97             altered_runs.append(True) 
    9832 
    9933 
  • trunk/test/zoo_fixture.py

    r426 r427  
    4545 
    4646import dejavu 
    47 from dejavu import errors, logic, storage 
     47from dejavu import errors, storage 
    4848from dejavu import Unit, UnitProperty, ToOne, ToMany, UnitSequencerInteger, UnitAssociation 
    4949from dejavu.test import tools 
    5050from dejavu import engines 
     51from geniusql import logic, logicfuncs 
     52logicfuncs.init() 
    5153 
    5254 
     
    463465             
    464466            # logic and other functions 
    465             self.assertEqual(matches(lambda x: dejavu.ieq(x.Species, 'slug')), 1) 
    466             self.assertEqual(matches(lambda x: dejavu.icontains(x.Species, 'PEDE')), 2) 
    467             self.assertEqual(matches(lambda x: dejavu.icontains(('Lion', 'Banana'), x.Species)), 1) 
    468             f = lambda x: dejavu.icontainedby(x.Species, ('Lion', 'Bear', 'Leopard')) 
     467            self.assertEqual(matches(lambda x: ieq(x.Species, 'slug')), 1) 
     468            self.assertEqual(matches(lambda x: icontains(x.Species, 'PEDE')), 2) 
     469            self.assertEqual(matches(lambda x: icontains(('Lion', 'Banana'), x.Species)), 1) 
     470            f = lambda x: icontainedby(x.Species, ('Lion', 'Bear', 'Leopard')) 
    469471            self.assertEqual(matches(f), 3) 
    470472            name = 'Lion' 
     
    476478            # Test now(), today(), year(), month(), day() 
    477479            self.assertEqual(matches(lambda x: x.Founded != None 
    478                                      and x.Founded < dejavu.today(), Zoo), 3) 
    479             self.assertEqual(matches(lambda x: x.LastEscape == dejavu.now()), 0) 
    480             self.assertEqual(matches(lambda x: dejavu.year(x.LastEscape) == 2004), 1) 
    481             self.assertEqual(matches(lambda x: dejavu.month(x.LastEscape) == 12), 1) 
    482             self.assertEqual(matches(lambda x: dejavu.day(x.LastEscape) == 21), 1) 
     480                                     and x.Founded < today(), Zoo), 3) 
     481            self.assertEqual(matches(lambda x: x.LastEscape == now()), 0) 
     482            self.assertEqual(matches(lambda x: year(x.LastEscape) == 2004), 1) 
     483            self.assertEqual(matches(lambda x: month(x.LastEscape) == 12), 1) 
     484            self.assertEqual(matches(lambda x: day(x.LastEscape) == 21), 1) 
    483485 
    484486             
     
    537539            expected = [u'Montr\xe9al Biod\xf4me', 'Wild Animal Park'] 
    538540            e = (lambda x: x.Founded != None 
    539                  and x.Founded <= dejavu.today() 
     541                 and x.Founded <= today() 
    540542                 and x.Founded >= datetime.date(1990, 1, 1)) 
    541543            values =  [val[0] for val in box.view(Zoo, ['Name'], e)] 
     
    772774        expected = [u'Montr\xe9al Biod\xf4me', 'Wild Animal Park'] 
    773775        e = (lambda x: x.Founded != None 
    774              and x.Founded <= dejavu.today() 
     776             and x.Founded <= today() 
    775777             and x.Founded >= datetime.date(1990, 1, 1)) 
    776778        values =  [val[0] for val in arena.view(Zoo, ['Name'], e)] 
  • trunk/views.py

    r426 r427  
    88import datetime 
    99import dejavu 
    10 from dejavu import errors, logic, recur 
     10from dejavu import errors, recur 
     11from geniusql import logic 
    1112 
    1213 
     
    4546 
    4647 
    47 class Sources(object): 
     48class ViewSource(object): 
    4849     
    4950    # This should be either a Unit class or a UnitJoin instance. 
    50     sources = None 
     51    value = None 
    5152     
    52     def __init__(self, sources): 
    53         self.sources = sources 
     53    def __init__(self, value): 
     54        self.value = value 
     55 
     56 
     57class ViewAttrs(object): 
     58     
     59    # This should be either a list of lists or a logic.Expression. 
     60    value = [] 
     61     
     62    def __init__(self, value): 
     63        if not isinstance(value, (list, tuple, logic.Expression)): 
     64            value = logic.Expression(value) 
     65        self.value = value 
    5466 
    5567 
     
    6577    # The following are equivalent to: 
    6678    # "SELECT Attributes FROM Relation WHERE Restriction" 
    67     Relation = dejavu.UnitProperty(Sources) 
     79    Relation = dejavu.UnitProperty(ViewSource) 
     80     
    6881    # At the moment, Attributes is a list (of lists, probably). 
    6982    # In the future, it might be a lambda instead in order to support 
    7083    # aggregation functions (possibly with GROUP BY?) 
    71     Attributes = dejavu.UnitProperty(list) 
     84    Attributes = dejavu.UnitProperty(ViewAttrs) 
     85     
    7286    Restriction = dejavu.UnitProperty(logic.Expression) 
    7387     
     
    91105        sm = arena.storage(self.__class__) 
    92106         
    93         sources = self.Relation.sources 
     107        sources = self.Relation.value 
    94108        if isinstance(sources, dejavu.UnitJoin): 
    95109            sources = sm.tablejoin(sources) 
     
    97111            sources = sm.schema[sources.__name__] 
    98112         
    99         newtable = sm.db.insert_into(name, sources, self.Attributes
     113        newtable = sm.db.insert_into(name, sources, self.Attributes.value
    100114                                     self.Restriction) 
    101115