diff --git a/Gemfile b/Gemfile
index 1d736fe..1c0d3d8 100644
--- a/Gemfile
+++ b/Gemfile
@@ -10,6 +10,8 @@ when "data_mapper"
 when "mongoid"
   gem "bson_ext", "~> 1.1"
   gem "mongoid", "~> 2.0.0.beta.19"
+else
+  raise "Unknown model adapter: #{ENV["MODEL_ADAPTER"]}"
 end
 
 gemspec
diff --git a/lib/cancan.rb b/lib/cancan.rb
index 4b3315c..a947157 100644
--- a/lib/cancan.rb
+++ b/lib/cancan.rb
@@ -7,6 +7,7 @@ require 'cancan/query'
 require 'cancan/inherited_resource'
 
 require 'cancan/model_adapters/abstract_adapter'
+require 'cancan/model_adapters/default_adapter'
 require 'cancan/model_adapters/active_record_adapter' if defined? ActiveRecord
 require 'cancan/model_adapters/data_mapper_adapter' if defined? DataMapper
 require 'cancan/model_adapters/mongoid_adapter' if defined? Mongoid
diff --git a/lib/cancan/ability.rb b/lib/cancan/ability.rb
index 0f9c321..039aa51 100644
--- a/lib/cancan/ability.rb
+++ b/lib/cancan/ability.rb
@@ -187,7 +187,8 @@ module CanCan
     end
 
     def model_adapter(model_class, action)
-      ModelAdapters::ActiveRecordAdapter.new(model_class, relevant_rules_for_query(action, model_class))
+      adapter_class = ModelAdapters::AbstractAdapter.adapter_class(model_class)
+      adapter_class.new(model_class, relevant_rules_for_query(action, model_class))
     end
 
     # See ControllerAdditions#authorize! for documentation.
diff --git a/lib/cancan/model_adapters/abstract_adapter.rb b/lib/cancan/model_adapters/abstract_adapter.rb
index 5ce0480..d350a4a 100644
--- a/lib/cancan/model_adapters/abstract_adapter.rb
+++ b/lib/cancan/model_adapters/abstract_adapter.rb
@@ -1,6 +1,20 @@
 module CanCan
   module ModelAdapters
     class AbstractAdapter
+      def self.inherited(subclass)
+        @subclasses ||= []
+        @subclasses << subclass
+      end
+
+      def self.adapter_class(model_class)
+        @subclasses.detect { |subclass| subclass.for_class?(model_class) } || DefaultAdapter
+      end
+
+      # Used to determine if the given adapter should be used for the passed in class.
+      def self.for_class?(member_class)
+        false # override in subclass
+      end
+
       def initialize(model_class, rules)
         @model_class = model_class
         @rules = rules
diff --git a/lib/cancan/model_adapters/active_record_adapter.rb b/lib/cancan/model_adapters/active_record_adapter.rb
index 180512e..a444e2e 100644
--- a/lib/cancan/model_adapters/active_record_adapter.rb
+++ b/lib/cancan/model_adapters/active_record_adapter.rb
@@ -1,6 +1,10 @@
 module CanCan
   module ModelAdapters
     class ActiveRecordAdapter < AbstractAdapter
+      def self.for_class?(model_class)
+        model_class <= ActiveRecord::Base
+      end
+
       # Returns conditions intended to be used inside a database query. Normally you will not call this
       # method directly, but instead go through ActiveRecordAdditions#accessible_by.
       #
diff --git a/lib/cancan/model_adapters/default_adapter.rb b/lib/cancan/model_adapters/default_adapter.rb
new file mode 100644
index 0000000..d76d87f
--- /dev/null
+++ b/lib/cancan/model_adapters/default_adapter.rb
@@ -0,0 +1,7 @@
+module CanCan
+  module ModelAdapters
+    class DefaultAdapter < AbstractAdapter
+      # This adapter is used when no matching adapter is found
+    end
+  end
+end
diff --git a/spec/cancan/ability_spec.rb b/spec/cancan/ability_spec.rb
index e022182..a77311b 100644
--- a/spec/cancan/ability_spec.rb
+++ b/spec/cancan/ability_spec.rb
@@ -343,6 +343,14 @@ describe CanCan::Ability do
     end
   end
 
+  it "should determine model adapter class by asking AbstractAdapter" do
+    model_class = Object.new
+    adapter_class = Object.new
+    stub(CanCan::ModelAdapters::AbstractAdapter).adapter_class(model_class) { adapter_class }
+    stub(adapter_class).new(model_class, []) { :adapter_instance }
+    @ability.model_adapter(model_class, :read).should == :adapter_instance
+  end
+
   describe "unauthorized message" do
     after(:each) do
       I18n.backend = nil
diff --git a/spec/cancan/model_adapters/active_record_adapter_spec.rb b/spec/cancan/model_adapters/active_record_adapter_spec.rb
index d256472..edc935d 100644
--- a/spec/cancan/model_adapters/active_record_adapter_spec.rb
+++ b/spec/cancan/model_adapters/active_record_adapter_spec.rb
@@ -33,6 +33,12 @@ if ENV["MODEL_ADAPTER"].nil? || ENV["MODEL_ADAPTER"] == "active_record"
       @comment_table = Comment.table_name
     end
 
+    it "should be for only active record classes" do
+      CanCan::ModelAdapters::ActiveRecordAdapter.should_not be_for_class(Object)
+      CanCan::ModelAdapters::ActiveRecordAdapter.should be_for_class(Article)
+      CanCan::ModelAdapters::AbstractAdapter.adapter_class(Article).should == CanCan::ModelAdapters::ActiveRecordAdapter
+    end
+
     it "should not fetch any records when no abilities are defined" do
       Article.create!
       Article.accessible_by(@ability).should be_empty
diff --git a/spec/cancan/model_adapters/default_adapter_spec.rb b/spec/cancan/model_adapters/default_adapter_spec.rb
new file mode 100644
index 0000000..b257353
--- /dev/null
+++ b/spec/cancan/model_adapters/default_adapter_spec.rb
@@ -0,0 +1,7 @@
+require "spec_helper"
+
+describe CanCan::ModelAdapters::DefaultAdapter do
+  it "should be default for generic classes" do
+    CanCan::ModelAdapters::AbstractAdapter.adapter_class(Object).should == CanCan::ModelAdapters::DefaultAdapter
+  end
+end