Gemli.Data v0.3.0 Released

by Jon Davis 12. October 2009 03:57

I reached a milestone this late night with The Gemli Project and decided to go ahead and release it. This release follows an earlier blog post describing some syntactical sugar that was added along with pagination and count support, here:

http://www.jondavis.net/techblog/post/2009/10/05/GemliData-Pagination-and-Counts.aspx

Remember those tests I kept noting that I still need to add to test the deep loading and deep saving functionality? No? Well I remember them. I kept procrastinating them. And as it turned out, I’ve discovered that a lesson has been taught to me several times in the past, and again now while trying to implement a few basic tests, a lesson I never realized was being taught to me until finally just this late night. The lesson goes something like this:

If in your cocky self-confidence you procrastinate the tests of a complex system because it is complex and because you are confident, you are guaranteed to watch them fail when you finally add them.

Mind you, the “system” in context is not terribly complex, but I’ll confess there was tonight a rather ugly snippet of code to wade through, particularly while Jay Leno or some other show was playing in the background to keep me distracted. On that latter note, it wasn’t until I switched to ambient music that I was finally able to fix a bug that I’d spent hours staring at.

This milestone release represents 130 total unit tests since the lifetime of the project (about 10-20 or so new tests, not sure exactly how many), not nearly enough but enough to feel a lot better about what Gemli is shaping in itself. I still yet need to add a lot more tests, but what these tests exposed was a slew of buggy relationship inferences that needed to be taken care of. I felt the urgency to release now rather than continue to add tests first because the previous release was just not suitably functional on the relationships side.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags: ,

C# | Cool Tools | Open Source | Pet Projects

Gemli.Data: Pagination and Counts

by Jon Davis 5. October 2009 03:54

It occurred to me that I’m not blogging enough about how Gemli is shaping, other than mentioning the project on the whole in completely different blog posts.

In the dev branch I’ve dropped the abstract base DataModelQuery class (only DataModelQuery<TModel> remains) and replaced it with an IDataModelQuery interface. This was a long-needed change, as I was really only using it for its interfaces anyway. It was being used because I didn’t necessarily know the TModel type until runtime, namely in the DataProviderBase class which handles all the deep loads with client-side-joins-by-default behavior. But an interface will work for that just as well, and meanwhile the query chaining syntax behavior was totally inconsistent and in some cases useless.

Some recent changes that have been made in the dev branch include some more syntactical sugar, namely the support for loading and saving directly from a DataModel/DataModel<T> class or from a DataModelQuery<TModel> plus support for pagination and getting record counts.

Quick Loads

From DataModel:

List<MyPoco> collectionOfMyPoco = DataModel<MyPoco>.LoadAll().Unwrap<MyPoco>();

There are also Load() and LoadMany() on DataModel, but since they require a DataModelQuery object as a parameter, and DataModelQuery has new SelectFirst() and SelectMany() that do the same thing (forward the task on to the DataProvider), I’m not sure they’re needed and I might just delete them.

From DataModelQuery:

List<MyPoco> collectionOfMyPoco = DataModel<MyPoco>.NewQuery()
    .WhereProperty["Amount"].IsGreaterThan(5000m)
    .SelectMany().Unwrap<MyPoco>();

Pagination

Since Gemli is being built for web development, pagination support with pagination semantics (“page 3”, rather than “the rows between rows X and Y”) is a must. There are many things besides data grids that require pagination—actually, pretty much any list needs pagination if you intend not to show as many items on a page as there are in a database table.

Client-side pagination is implemented by default, but only if DB server-side pagination is not handled by the data provider. I still intend to add DB-side pagination for SQL Server.

// get rows 61-80, or page 4 @ 20 items per page, of my filtered query
var myListOfStuff = DataModel<Stuff>.NewQuery()
    .WhereProperty["IsActive"].IsEqualTo(true)
    .Page[4].OfItemsPerPage(20)
    .SelectMany().Unwrap<Stuff>();

To add server-side pagination support for a proprietary database, you can inherit DbDataProvider and override the two variations of CreateCommandBuilder() (one takes a DataModel for saving, the other takes a DataModelQuery for loading). The command builder object has a HandlePagination property that can be assigned a delegate. The delegate would then add or modify properties in the command builder that inject appropriate SQL text into the command.

Count

Support for a basic SELECT COUNT(*) FROM MyTable WHERE [..conditions..] is a pretty obvious part of any minimal database interaction library (O/RM or what have you). For this reason, GetCount<TModel>(DataModelQuery query) has been added to DataProviderBase, and in DbDataProvider it replaces the normal LoadModel command builder generated text with SELECT COUNT(*)…  The DataModelQuery<TModel> class also has a new SelectCount() method which forwards the invocation to the DataProvider.

long numberOfPeepsInMyNetwork = DataModel<Person>.NewQuery()
    .WhereProperty["Networkid"].IsEqualTo(myNetwork.ID)
    .SelectCount();

All of these changes are still pending another alpha release later. But if anyone wants to tinker it’s all in the dev branch in source code at http://gemli.codeplex.com/ .

LINQ May Be Coming

I still have a lot of gruntwork to do to get this next alpha built, particularly in adding a lot more tests. I still haven’t done enough testing of deep loads and deep saves and I’m not even confident that deep saves are working correctly at the basic level as I haven’t yet used them. Once all of that is out of my way, I might start looking at adding LINQ support. I’m not sure how awfully difficult LINQ support will prove to be yet, but I’m certain that it’s doable.

One of the biggest advantages of LINQ support is strongly typed member checking. For example, in Gemli, you currently have to declare your WHERE clauses with a string reference to the member name or the column name, whereas with LINQ the member name can be referenced as strongly-typed code. As far as I know, it does this by way of syntactic sugar that ultimately boils down to delegates that literally work with the object directly, depending on how the LINQ support was added.

Among the other advantages of adding LINQ support might be in adding support for anonymous types. For example, right now without LINQ you’re limited to DataModels and the class structures they represent. But LINQ lets you select specific members into your return object, for example, rather than the whole enchilada.

LINQ:

// only return ID and Name, not the whole Product
var mySelection = (from p in Product
                   select p.ID, p.Name).ToList();

It’s this underlying behavior that creates patterns for me to work with that I might drag into play the support for aggregate functions in SQL using terse Gemli+LINQ semantics. Right now, it’s literally impossible for Gemli to select the result of an aggregate function (other than Count(*)) unless that was wrapped in a stored procedure on the DB side and then wrapped in a DataModel on Gemli’s side. There’s also no GROUP BY support, etc. I like to believe that LINQ will help me consolidate the interface patterns I need to make all that work correctly. However, so far I’m still just one coder as no one has jumped on board with Gemli yet so we’ll see if LINQ support makes its way in at all.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags: ,

Pet Projects | Software Development

Gemli Project v0.2 Released

by Jon Davis 21. September 2009 03:57

Earlier this late night I posted the first major overhaul update of Gemli since a month ago. This brings a huge number of design fixes and new features to Gemli.Data and makes it even more usable. It's still alpha, though, as there's a lot more testing to be done, not to mention still some new features to be added.

http://gemli.codeplex.com/Release/ProjectReleases.aspx?ReleaseId=33281

From the release notes:

  • Added to DataProviderBase: SupportsTransactions { get; } , BeginTransaction(), and BeginTransaction(IsolationLevel)
  • Facilitate an application default provider: Gemli.Data.Providers.ProviderDefaults.AppProvider = myDBProvider .. This allows DataModels and DataModelCollections to automatically use the application's data provider when one hasn't already been associated with the model (so you can, for example, invoke .Save() on a new model without setting its provider manually)
  • Replace (and drop) TypeConvertor with DbTypeConverter.
  • Operator overloads on DataModelQuery; you can now use == instead of IsEqualTo(), but this comes at the cost of chainability. (IsEqualTo() is still there, and still supports chaining.)
  • Added SqlDbType attribute property support. DataType attribute value is no longer a DbType and is instead a System.Type. The properties DbType and SqlDbType have been added, and setting any of these three properties will automatically translate and populate the other two.
  • DataType attribute value is no longer a DbType and is instead a System.Type. The properties DbType and SqlDbType have been added, and setting any of these three properties will automatically translate and populate the other two.
  • WhereMappedColumn is now WhereColumn
  • Facilitate optional behavior of inferring from all properties not marked as ignore, rather than the behavior or inferring from none of the unattributed properties unless no properties are attributed. The latter behavior--the old behavior--currently remains the default. The new behavior can be applied with DataModelTableMappingAttribute's PropertyLoadBehavior property
    • This may change to where the default is InferProperties.NotIgnored (the new behavior), still pondering on this.
  • Add sorting to MemoryDataProvider
  • TempMappingTable is now DataModelMap.RuntimeMappingTable
  • ForeignDataModel.ForeignXXXX was backwards and is now RelatedXXXX (multiple members)
  • DataModelFieldMappingAttribute is now DataModelColumnAttribute.
  • DataModelMap.FieldMappings is now DataModelMap.ColumnMappings.
  • DataModelTableMappingAttribute is now DataModelTableAttribute.
  • DataModelForeignKeyAttribute is now ForeignKeyAttribute.
  • The XML serialization of all elements now follows these renamings and is also now camelCased instead of ProperCase.
  • XML loading of mapping configuration is getting close, if it isn't already there. Need to test.
  • Added DataModelMap.LoadMappings(filePath)

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags: ,

C# | Cool Tools | Pet Projects | Software Development

Introducing The Gemli Project

by Jon Davis 23. August 2009 21:11

I’ve just open-sourced my latest pet project. This project was started at around the turn of the year, and its scope has been evolving over the last several months. I started out planning on a framework for rapid development and management of a certain type of web app, but the first hurdle as with anything was picking a favorite DAL methodology. I tend to lean towards O/RMs as I hate manually managed DAL code, but I didn’t want to license anything (it’d mean sublicensing if I redistribute what I produce), I have some issues with LINQ-to-SQL and LINQ-to-Entities, I find nHibernate difficult to swallow, I have some reservations about SubSonic, and I just don’t have time nor interest to keep perusing the many others. Overall, my biggest complaint with all the O/RM offerings, including Microsoft’s, is that they’re too serious. I wanted something lightweight that I don’t have to think about much when building apps.

So as a project in itself I decided first to roll my own O/RM, in my own ideal flavor. Introducing Gemli.Data! It’s a lightweight O/RM that infers as much as possible using reflection, assumes the most basic database storage scenarios, and helps me keep things as simple as possible.

That’s hype-speak to say that this is NOT a “serious O/RM”, it’s intended more for from-scratch prototype projects for those of us who begin with C# classes and want to persist them, and don’t want to fuss with the database too much.

I got the code functioning well enough (currently 92 unit tests, all passing) that I felt it was worth it to go ahead and let other people start playing with it. Here it is!

Gemli Project Home: http://www.gemli-project.org/ 

Gemli Project Code: http://gemli.codeplex.com/

Gemli.Data is currently primarily a reflection-based mapping solution. Here’s a tidbit sample of functioning Gemli.Data code (this comes from the CodePlex home page for the project):

// attributes only used where the schema is not inferred
// inferred: [DataModelTableMapping(Schema = "dbo", Table = "SamplePoco")]
public class SamplePoco
{
    // inferred: [DataModelFieldMapping(ColumnName = "ID", IsPrimaryKey = true, IsIdentity = true, 
    //     IsNullable = false, DataType = DbType.Int32)] // note: DbType.Int32 is SQL type: int
    public int ID { get; set; }

    // inferred: [DataModelFieldMapping(ColumnName = "SampleStringValue", IsNullable = true, 
    //     DataType = DbType.String)] // note: DbType.String is SQL type: nvarchar
    public string SampleStringValue { get; set; }

    // inferred: [DataModelFieldMapping(ColumnName = "SampleDecimalValue", IsNullable = true, 
    //     DataType = DbType.Decimal)] // note: DbType.Decimal is SQL type: money
    public decimal? SampleDecimalValue { get; set; }
}

[TestMethod]
public void CreateAndDeleteEntityTest()
{
    var sqlFactory = System.Data.SqlClient.SqlClientFactory.Instance;
    var dbProvider = new DbDataProvider(sqlFactory, TestSqlConnectionString);

    // create my poco
    var poco = new SamplePoco { SampleStringValue = "abc" };

    // wrap and auto-inspect my poco
    var dew = new DataModel<SamplePoco>(poco); // data entity wrapper

    // save my poco
    dew.DataProvider = dbProvider;
    dew.Save(); // auto-synchronizes ID
    // or...
    //dbProvider.SaveModel(dew);
    //dew.SynchronizeFields(SyncTo.ClrMembers); // manually sync ID

    // now let's load it and validate that it was saved
    var mySampleQuery = DataModel<SamplePoco>.NewQuery()
        .WhereProperty["ID"].IsEqualTo(poco.ID); // poco.ID was inferred as IsIdentity so we auto-returned it on Save()
    var data = dbProvider.LoadModel(mySampleQuery);
    Assert.IsNotNull(data); // success!

    // by the way, you can go back to the POCO type, too
    SamplePoco poco2 = data.Entity; // no typecast nor "as" statement
    Assert.IsNotNull(poco2);
    Assert.IsTrue(poco2.ID > 0);
    Assert.IsTrue(poco2.SampleStringValue == "abc");

    // test passed, let's delete the test record
    data.MarkDeleted = true; 
    data.Save();

    // ... and make sure that it has been deleted
    data = dbProvider.LoadModel(mySampleQuery);
    Assert.IsNull(data);

}

Gemli.Data supports strongly typed collections and multiple records, too, of course.

var mySampleQuery = DataModel<SamplePoco>.NewQuery()
    .WhereMappedColumn["SampleStringValue"].IsLike("%bc");
var models = dbProvider.LoadModels(mySampleQuery);
SamplePoco theFirstSamplePocoEntity = models.Unwrap<SamplePoco>()[0];
// or.. SamplePoco theFirstSamplePocoEntity = models[0].Entity;

Anyway, go to the URLs above to look at more of this. It will be continually evolving.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags: , , ,

C# | Open Source | Software Development | Pet Projects

CAPTCHA This, Yo! - Early Alpha

by Jon Davis 14. July 2009 01:54

I've posted a mini-subproject:

http://www.CAPTCHAThisYo.com/

The site is self-explanatory. The idea is simple. I want CAPTCHA. I don't want to support CAPTCHA in my apps. I just want to drop in a one-liner snippet somewhere and call it done. I think other people share the same desire. So I now support CAPTCHA as a CAPTCHA app. I did all the work for myself so that I don't have to do that work. I went through all that trouble so that I don't have to go through the trouble .... Wait, ...

Seriously, it's not typical CAPTCHA, and it's Not Quite Done Yet (TM). It's something that'll evolve. Right now there isn't even any hard-to-read graphic CAPTCHA.

But what I'd like to do is have an ever-growing CAPTCHA questions library and, by default, have it just rotate through them randomly. The questions might range from shape detection to riddles to basic math. I'd really like to have some kind of community uploads thingmajig with ratings, so that people can basically share their own CAPTCHA solutions and they all run inside the same captchathisyo.com CAPTCHA engine. I'm just not sure yet how to pull that off.

Theoretically, I could take the approach Microsoft took when C# was initially released (long, long ago, in a galaxy far, far away), they had a cool insect sandbox game where you could write a .NET class that implements some interface and then send it up to the server and it would just run as an insect on the server. The objective of the game was to write the biggest killer/eater. I'm not sure how feasible the idea is of opening up all .NET uploads to the server, but it's something I'm pondering on.

Anyway, the concept has been prototyped and the prototype has been deployed is sound, but I still need to work out cross-site scripting limitations, bear with me. I still need to find a designer to make something beautful out of it. That said, feel free to use it and give feedback. Stand by.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

C# | Computers and Internet | Cool Tools | Pet Projects | Techniques | Web Development

Nail-biting success with Windows 7 Media Center and CableCard

by Jon Davis 22. June 2009 01:34

I got CableCard working today with Windows 7 Media Center. This is my first CableCard install. The install was not smooth, but it was successful. I'd heard a lot of horror stories about CableCard, but most of these stories were from two years or so ago. I expected the whole matter to be cleaned up by now. It has probably improved a lot, but I was surprised by how bumpy the ride was.

...

COX technicians really, genuinely, deeply hate CableCards. This was the first visit to install CableCard, but the second visit from COX in the last couple weeks where the subject of CableCards came up. These guys acknowledge that the idea behind CableCard is a sound one, but the problem is that they are so different, and the devices are so different, that it's really hard to get a successful install. [I think Microsoft can relate to this sort of experience, being that their software works with most any white box PC on the planet.] Today's installer had a nauseous-looking frown on his face consistently from the moment he climbed the outer stairs to my door until the minute he walked out the door.. although, he had a slight skip in his step when he left. I'm not sure if that's because he was glad the torture was over or if it was because it wasn't another failure.

More at: http://thegreenbutton.com/forums/thread/370299.aspx

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags: ,

Electronics | General Technology | Pet Projects

Quickie Alarm

by Jon Davis 13. May 2009 23:39

I flew out to California on Friday night to visit my siblings, and when I arrived I rented a car and drove around in the middle of the night looking for a cheap place to sleep. After an hour of getting completely lost I finally found a Motel 6 (*shudder*), climbed into bed, and then realized that there’s no alarm clock in the room. Great.

So I threw together another alarm clock on my laptop. I went through the trouble of giving it a nice touch, so it took an hour or two rather than a minute or two, but it did the job and I was proud and still managed to sleep well.

And now I’m sharing it here online. This is freeware with source code included. (Uses free Developer Express controls.)

image

.. click ‘Go’ and ..

image

Download: http://www.jondavis.net/codeprojects/QuickieAlarm/QuickieAlarm.zip

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

Open Source | Cool Tools | Pet Projects

Stupid Visual Studio Tricks: Speak ‘N Code

by Jon Davis 7. March 2009 01:58

I got bored tonight and created a Visual Studio macro that reads my code to me as I type it. First I had it read the keys (“a”, “b”) like a Speak ‘N Spell, but then I realized it’s better if it actually just waits for me to spell out the words instead. It also correctly pronounces a few special characters.

I have absolutely no use for this but for “duhh huh huh huh” giggles.

If you care to play with it, just open Visual Studio, choose Tools –> Macros –> Macros IDE from the menu, double-click MyMacros on the left, double-click EnvironmentEvents, then paste the following code inside the module body.

Private Speech As Object

Private Sub TextDocumentKeyPressEvents_BeforeKeyPress(ByVal Keypress _
As String, ByVal Selection As EnvDTE.TextSelection, _
ByVal InStatementCompletion As Boolean, ByRef CancelKeyPress As Boolean) _
Handles TextDocumentKeyPressEvents.BeforeKeyPress
    If Speech Is Nothing Then
        Speech = Activator.CreateInstance(Type.GetTypeFromProgID("sapi.spvoice"))
        Speech.Voice = Speech.GetVoices("gender=male")(0)
    End If
    Dim Key As String
    Key = Keypress
    If Key = vbBack Then Return
    Select Case Keypress
        Case "!"
            Key = "not"
        Case "%"
            Key = "mod"
        Case "@"
            Key = "at"
        Case "#"
            Key = "pound"
        Case "^"
            Key = "caret"
        Case "&"
            Key = "and"
        Case "*"
            Key = "star"
        Case "/"
            Key = "slash"
        Case "\"
            Key = "backslash"
        Case ","
            Key = "comma"
        Case "<"
            Key = "less than"
        Case ">"
            Key = "greater than"
        Case ":"
            Key = "colon"
        Case "("
            Key = "" ' "pahrens"
        Case ")"
            Key = "" ' "close pahrens"
        Case "."
            Key = "dot"
        Case "{"
            Key = "" ' "begin brace"
        Case "}"
            Key = "" ' "close brace"
        Case ";"
            Key = "" ' "semicolon"
        Case vbTab
            Key = "" ' "tab"
        Case " "
            Key = "" ' "space"
        Case "["
            Key = "" ' "left bracket"
        Case "]"
            Key = "" ' "right bracket"
        Case """"
            Key = "" ' "double quotes"
        Case "'"
            Key = "single quote"
        Case vbCr, vbLf, vbCrLf
            Key = "" ' "line break"
    End Select
    Dim Say As String
    Const a2z As String = "abcdefghijklmnopqrstuvwxyz"
    If Not a2z.Contains(Keypress.ToLower()) Then
        Say = Key
        Dim editPoint = Selection.ActivePoint().CreateEditPoint()
        editPoint.CharLeft()
        If Not IsWhitespace(editPoint.GetText(1)) Then
            editPoint.CharRight()
            editPoint.WordLeft()
            Dim Word = editPoint.GetText(Selection.ActivePoint.AbsoluteCharOffset - editPoint.AbsoluteCharOffset)
            Dim HasLetter As Boolean
            For Each letter In Word
                If a2z.Contains(letter) Then HasLetter = True
            Next
            If HasLetter Then
                If Not IsWhiteSpace(Keypress) Then
                    Say = Word & ", " & Say
                Else
                    Say = Word
                End If
            End If
        End If

    End If

    If Say <> "" Then
        Speech.Speak(Say, SpeechVoiceSpeakFlags.SVSFlagsAsync + SpeechVoiceSpeakFlags.SVSFPurgeBeforeSpeak)
    End If
End Sub

Function IsWhitespace(ByVal s As String)
    Dim rgx As New System.Text.RegularExpressions.Regex("\s*")
    Return rgx.Match(s).Length > 0
End Function

Enum SpeechVoiceSpeakFlags
    'SpVoice Flags
    SVSFDefault = 0
    SVSFlagsAsync = 1
    SVSFPurgeBeforeSpeak = 2
    SVSFIsFilename = 4
    SVSFIsXML = 8
    SVSFIsNotXML = 16
    SVSFPersistXML = 32

    'Normalizer Flags
    SVSFNLPSpeakPunc = 64

    'Masks
    SVSFNLPMask = 64
    SVSFVoiceMask = 127
    SVSFUnusedFlags = -128
End Enum

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

VB.NET | Pet Projects

EntitySpaces 2009 Q1 WCF Demo

by Jon Davis 25. January 2009 16:45

I created a new WCF demo for EntitySpaces, one of the most popular ORM solutions available for .NET which now comes with its own code generator (no longer relies on CodeSmith or myGeneration). The demo is bundled in the Release Candidate for v2009 Q1. (The developer version is released, trial version will be released tomorrow.) This one includes both console and Windows Forms clients, and a console-based service, for showing the barebones basics of what it takes to get EntitySpaces working with WCF. Both full proxies (EntitySpaces runtime libraries referenced on the client) and lightweight proxies/stubs (*no* EntitySpaces runtime libraries referenced on the client) are demonstrated, but the lightweight demo is currently limited to a console app.

Next on my plate will be a WPF demo for the lightweight proxies/stubs. No guarantees...

Anyway, here’s the documentation that went with the demo. It got posted on the EntitySpaces blog.

http://www.entityspaces.net/blog/2009/01/25/EntitySpaces+2009+And+WCF.aspx

Currently rated 5.0 by 1 people

  • Currently 5/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags:

C# | Cool Tools | Pet Projects | Software Development | SQL Server | WCF

Update on my stuff - June 6, 2008

by Jon Davis 7. June 2008 14:29

OK it's been a while since I did any real blogging lately, here's a sum-up:

  • I've still forgotten how to blog. While this is my blog and I can post whatever I want, this blog has become a high-level geek toy discovery dump rather than a software development blog. While I make no apologies for this--I can do whatever I want here--I'm trying to figure out if I should fork my blogs, one for serious software development discoveries and one for shallow geek discoveries. I've already been wishing I could add a personal blog somewhere, not here, and post thoughts and feelings about non-tech stuff. (This is something I used to do but it got carried away so I boycotted it and focused on purely geek speak here. I miss doing personal blogging though, and I feel like it would be good for me to do it again, if I'm just a bit more careful.)
     
  • I keep mentioning the LION Search Service, how we intend to open source it, and how it's been cancelled, and then I deleted that cancellation post, etc. It keeps coming back and going away and coming back again. Well part of that is just the reality of how it's being treated at the office; open sourcing LION required all-or-nothing support on the part of my teammates at the office, and I was getting really pointless "I'm building my own search service instead of yours but I'm gleaning ideas from yours" feedback from others on the team. Lately, though, they've discovered that what they were doing was accomplishing the same tasks as what I had already implemented, and in the absence of time availability they reverted and have adopted LION. So LION is back, the team has adopted it, and we're about to go live with our first faceted-searching web site using LION (a couple other web sites were already using it but without the new faceted searching). It's now a lot more official, LION is our exciting new search platform going forward.

    So,
    • LION is a nearly-sort-of-enterprise-class search engine, written in C#, currently in development, built on Lucene.NET, and its continued development is being inspired in part by the Apache Solr project (but was conceived and put into production before Solr was discovered).
      • It currently offers
        • rich, paginated queries with field and index selection,
        • Lucene.NET break-neck speeds,
        • faceted searching,
        • strong document modeling, and
        • dynamic updates (currently limited to index A/B switching but that will be improved soon).
      • It currently runs on WCF (.NET 3.0). Not BizTalk or anything otherwise weird or expensive to support. It currently does not have, but will soon have, REST and AJAX support.
      • It does not have and might not ever have the high availability "server farm" feature set that I believe Solr offers. Service stability and uptime has been a constant thorn in our sides, so rethinking and possibly rewriting portions of the service itself is going to be necessary before we put it out there for the world to consume in open source.
      • It is currently not, but soon will be, built around IIS 7. Right now it's just a standalone console application, wrapped in a Windows service.
    • We will still be open-sourcing LION, eventually. Right now it's looking like a late-summer or fall time frame.
    • LION will be "internally sourced" first, to be shared to other departments in our large and disperate company, to be evaluated and discovered first. (I think this is very wise, just something I didn't think about until the boss said to do it that way.)
    • LION has been made a team-shared ownership; since I built it on the job, there's little I can do to stop the boss from handing it to a certain other team member and telling him to own it, which would be totally unsurprising. While I wouldn't agree with the situation (I've only put my heart and soul into LION, and I'm also the oldest and most experienced person on the team, even if I have a couple areas of technical weaknesses), a situation like that is not something I can change without throwing the baby out with the bathwater, and I'll live.
        
  • I've been thinking about engaging in one or more side projects I would wholly and independently control. Given the big ideas I have, I'm still not sure I want to do one, though, as it's all a lot of work, some of it very tempting to try to bring into the workplace, and I don't want my authortitative work to be disrespected in the workplace like LION has been. Even so, the ideas are still on the table for consideration
      
    • BlogObjects - I registered BlogObjects.net back when I registered PowerBlog.net (I wrote in VB6 and rewrote in C# a commercial blogging desktop client application about five years or so ago, with zero commercial success but significant personal/professional technical growth for myself) and was considering making PowerBlog's development API a set of open-source blogging tools. I'm thoroughly persuaded that this will never be commercially viable as blogging APIs are a dime a dozen, but, like PowerBlog was five years ago, starting from scratch on a client/server blogging API would be a good refresher on technology in general. This is something that, if I do it, it will be not only open source, it will also be cross-platfom to Mac and to Linux, and will also be complemented with a PowerBlog resurrection or else PowerBlog-like alternative with fewer feature (no Active Scripting [VBScript, Javascript], no team synchronization support).
        
    • CMSObjects - Taking BlogObjects to another level, CMSObjects would build upon BlogObjects's idea (but not the codebase) and add:
      • An enterprise class CMS service
      • Rich support for the Atom Publishing standard API
      • Content typing (for example, a "Story" article type, a "Video browser", a "Photo gallery", a "Product Detail" page, etc), with scripted or compiled coded definitions that support inheritence
      • Rich templating both per content type and per content instance
      • Workflows
        • Team member security (user can post, user can only read, user can only post to a particular category or to a particular URL prefix, etc.)
        • Team members' posts can be flagged for approval, and then approved by a senior editor
        • Content can be annotated, seperately from the publshed output -- ideally, the annotations can be made inline, directly inside of the content
        • Content publishing to the web can be postponed to a digital publish date
      • Content versioning 
      • Again, completely open-sourced, but more web service oriented, possibly web-driven, and much less GUI-driven (so no PowerBlog for CMSObjects except for basic blogging to a CMSObjects service)
          
    • CRMObjects - Yeah the "Objects" suffix is getting a little silly, but my short experience with Sage Software's SalesLogix exposed me to another facet of software and business technology that reflects the genuine needs of businesses in general, which is using technology to support sales and support staff. CRM can be painfully messy and awkward, but tossing together some basic building blocks might be a fun and rewarding experience, even if it is not commercially viable (way too much competition, as with blogging). Who knows, though, businesses might actually use it, and supporting it could actually become lucrative.
        
    • ERPObjects - I'll do that by myself, in my spare time. Just kidding.
        
  • I have a book here on Cocoa programming. I'm curious about Objective-C, how it's a weakly typed, object-oriented C language superset, which just sounds weird (C being object oriented and weakly typed?! .. weird! .. but cool!!), I can see why the book comes right out and says that it can be extremely dangerous, I saw enough of this with VB6 programming's suport for weak typing and evil Variants in my past, but keeping in line with C linguistics and C power, I'm very curious about it. I'm guessing that Microsoft's answer to Objective-C is C++/CLI, but the CLI in itself is still strongy typed, so you have to look at integration points with JScript.NET or something (but then there's Lua, Python, etc., which the non-Microsoft community also has). I watched an introduction to Objective-C video amongst the iPhone SDK videos recently and, while it does look different, I can see how it as been used to give Mac and iPhone developers a lot of shortcuts into fast and efficient software development.
      
  • Over the last two or three weeks I've become less and less excited about cross-platform development libraries and APIs, such as Mono, Java, wxWidgets, Qt4, and SDL, for a few reasons:
    • While cross-platform GUI APIs pretty actually do work across platforms like they promise, their end output is a bit less predictable and/or desirable than one might expect.
      • Choosing a GUI API that uses its own UI rendering results in software that can be predicted by the developer, but it is not predictable by the user in the context of other software. Java Swing apps traditionally demonstrated this a long while back with is blueish, proprietary look and feel, and that's not what users want. Users want software that looks and feel like the software already installed on their systems. Sometimes these cross-platform APIs, like Java, come bundled with visual schemes that simulate these operating systems, but they are clearly faked and do not take advantage of the rendering APIs already offered by the core operating system.
      • Choosing a GUI API that uses the operating system's rendering and layouts (such as how the Mac uses the Aqua scheme but also puts the main menu up on the top of the screen) does not always result in predictable rendering output. Sometimes, for example, the borders or clickable "handles" of a drop-down list sticks out further to the right, above, or below the dimensions specified by the developer, or else the text rendering inside becomes unreadable because the internal padding or inner/inset "border" that contains the content is too small on one operating system while on the developer's operating system it appears fine. Sometimes there is somehow a mismatch of pixels to DPI, and the GUI code is using one unit of measure while the OS has adopted another, and so some "defensive layout programming" needed to have been written but wasn't because the developer's operating system didn't have this or that feature. And so on.
    • Java and C# are both still too slow for my liking, and other non-native languages are not mainstream enough to feel confident in building around with the knowledge that others can help carry the torch.
    • I've found that some cross-platform software applications that use generically cross-platform dependencies such as SDL are actually quite unstable. This doesn't mean that SDL et al are unstable, it just means that it is too easy for developers to build upon such a framework and not hash out platform-specific causes to application failures. There is no such thing as a silver bullet, SDL/wx/Qt/etc notwithstanding.
    • Ultimately, C and C++ (but not Objective-C) are themselves cross-platform languages, with platform-specific dependencies (and, of course, CPU-specific machine code compilation). The best thing to do, I think, is to get a handle on building C++ applications for one platform, but build things out generically enough so that platform-specific dependencis are broken off into libraries. Then, when porting the applications, you only need to port the platform libraries. This is what most cross-platform software I've seen ends up doing when they also take advantage of the features of the operating system like DirectX.
    • Another approach might be to build upon a cross-platform API first, or perhaps even a cross-platform non-native language like C#, and then port each component, piece by piece, to C++ on behalf of the native patform.
    • None of this is to say that I think wx, Qt, SDL, et al, are worthless or that I won't use them on a regular basis (if indeed I can get myself coding C/C++ apps to begin with), I'm just trying to say that there is no silver bullet and use of these libraries, rather than native Cocoa (for Mac) or MFC (et al, for Windows), would be a slight compromise for time and resources, not a magical, perfect answer for excellent software that "just works".
        
  • At the end of the day, I'm still scratching the surface and barely finding time enough to sleep, much less write the software I'm envisioning. Ugh.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags: , , , , , , ,

Pet Projects | Software Development


 

Powered by BlogEngine.NET 1.4.5.0
Theme by Mads Kristensen

About the author

Jon Davis Jon Davis (aka "stimpy77") has been a programmer, developer, and consultant for web and Windows software solutions professionally since 1997, with experience ranging from OS and hardware support to DHTML programming to IIS/ASP web apps to Java network programming to Visual Basic applications to C# desktop apps.
 
Software in all forms is also his sole hobby, whether playing PC games or tinkering with programming them. "I was playing Defender on the Commodore 64," he reminisces, "when I decided at the age of 12 or so that I want to be a computer programmer when I grow up." 

Amazon Collection

Most Recent of Many Library Investments

Tag cloud

Calendar

<<  March 2010  >>
MoTuWeThFrSaSu
22232425262728
1234567
891011121314
15161718192021
22232425262728
2930311234

View posts in large calendar