Permalink
Browse files

Initial commit: started by defining some meta data, no injection yet.

  • Loading branch information...
0 parents commit 66e4db3142e242baad671e0f2611ce986468671e @psyho committed Apr 13, 2011
@@ -0,0 +1,4 @@
+pkg/*
+*.gem
+.bundle
+.rvmrc
@@ -0,0 +1,4 @@
+source "http://rubygems.org"
+
+# Specify your gem's dependencies in dependor.gemspec
+gemspec
@@ -0,0 +1,24 @@
+PATH
+ remote: .
+ specs:
+ dependor (0.0.1)
+
+GEM
+ remote: http://rubygems.org/
+ specs:
+ diff-lcs (1.1.2)
+ rspec (2.5.0)
+ rspec-core (~> 2.5.0)
+ rspec-expectations (~> 2.5.0)
+ rspec-mocks (~> 2.5.0)
+ rspec-core (2.5.1)
+ rspec-expectations (2.5.0)
+ diff-lcs (~> 1.1.2)
+ rspec-mocks (2.5.0)
+
+PLATFORMS
+ ruby
+
+DEPENDENCIES
+ dependor!
+ rspec
@@ -0,0 +1,11 @@
+require 'bundler'
+Bundler::GemHelper.install_tasks
+
+require 'rspec/core'
+require 'rspec/core/rake_task'
+
+desc "Run all specs"
+RSpec::Core::RakeTask.new(:spec) do |t|
+ t.pattern = "./spec/**/*_spec.rb"
+ t.rspec_opts = ["--profile --color --format=documentation"]
+end
@@ -0,0 +1,23 @@
+# -*- encoding: utf-8 -*-
+$:.push File.expand_path("../lib", __FILE__)
+require "dependor/version"
+
+Gem::Specification.new do |s|
+ s.name = "dependor"
+ s.version = Dependor::VERSION
+ s.platform = Gem::Platform::RUBY
+ s.authors = ["Adam Pohorecki"]
+ s.email = ["adam@pohorecki.pl"]
+ s.homepage = "http://github.com/psyho/dependor"
+ s.summary = %q{A simple, setter-based dependency injection framework}
+ s.description = %q{A framework for doing Dependency Injection in environments non-ioc-container friendly, like Rails. It allows you to write much faster, truly unit tests.}
+
+ s.rubyforge_project = "dependor"
+
+ s.add_development_dependency 'rspec'
+
+ s.files = `git ls-files`.split("\n")
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
+ s.require_paths = ["lib"]
+end
@@ -0,0 +1,8 @@
+require 'dependor/injectable.rb'
+require 'dependor/meta_data.rb'
+
+module Fake
+end
+
+module Dependor
+end
@@ -0,0 +1,33 @@
+module Dependor
+ module Injectable
+
+ def self.included(klass)
+ klass.send(:include, InstanceMethods)
+ klass.extend ClassMethods
+ end
+
+ module InstanceMethods
+ def inject!
+ self
+ end
+ end
+
+ module ClassMethods
+
+ def dependor_meta_data
+ @dependor_meta_data ||= Dependor::MetaData.new(self)
+ end
+
+ def depends_on(*dependency_names)
+ attr_accessor *dependency_names
+ dependency_names.each { |name| dependor_meta_data.add_dependency(name) }
+ end
+
+ def make
+ new.inject!
+ end
+
+ end
+
+ end
+end
@@ -0,0 +1,38 @@
+module Dependor
+
+ class MetaData
+ def initialize(klass)
+ @dependencies = Set.new
+ @klass = klass
+ end
+
+ def add_dependency(name)
+ @dependencies.add(name)
+ end
+
+ def dependencies
+ @dependencies + superclass_dependencies
+ end
+
+ def self.for(klass)
+ if klass.respond_to?(:dependor_meta_data)
+ return klass.dependor_meta_data
+ else
+ return EmptyMetaData.new
+ end
+ end
+
+ private
+
+ def superclass_dependencies
+ self.class.for(@klass.superclass).dependencies
+ end
+ end
+
+ class EmptyMetaData
+ def dependencies
+ Set.new
+ end
+ end
+
+end
@@ -0,0 +1,3 @@
+module Dependor
+ VERSION = "0.0.1"
+end
@@ -0,0 +1,87 @@
+require File.expand_path('../../spec_helper.rb', __FILE__)
+
+describe Dependor::Injectable do
+
+ class Foo
+ def name
+ "world"
+ end
+ end
+
+ class Fake::Foo
+ def name
+ "fake"
+ end
+ end
+
+ class Bar
+ include Dependor::Injectable
+
+ depends_on :foo
+
+ def hello
+ return "Hello #{foo.name}!"
+ end
+ end
+
+ class Fake::Bar
+ def hello
+ "Hello?"
+ end
+ end
+
+ class Baz
+ include Dependor::Injectable
+
+ depends_on :bar
+ end
+
+ describe ".make" do
+ let(:baz) { Baz.make }
+
+ it "should create objects with all dependencies satisfied" do
+ baz.bar.should be_an_instance_of(Bar)
+ end
+
+ it "should inject every object in the hierarchy" do
+ baz.bar.foo.should be_an_instance_of(Foo)
+ end
+ end
+
+ describe "declaring dependencies" do
+ class DeclaringDependenciesSample
+ include Dependor::Injectable
+
+ depends_on :foo, :bar
+ depends_on :baz
+ end
+
+ it "should add getters for all of the dependencies" do
+ sample = DeclaringDependenciesSample.new
+
+ sample.should respond_to(:foo)
+ sample.should respond_to(:bar)
+ sample.should respond_to(:baz)
+ end
+ end
+
+ describe "dependency inheritance" do
+ class DependencyInheritanceParent
+ include Dependor::Injectable
+
+ depends_on :foo
+ end
+
+ class DependencyInheritanceChild < DependencyInheritanceParent
+ depends_on :bar
+ end
+
+ it "should inject both parent and child dependencies" do
+ sample = DependencyInheritanceChild.new
+
+ sample.foo.should be_an_instance_of(Foo)
+ sample.bar.should be_an_instance_of(Bar)
+ end
+ end
+
+end
@@ -0,0 +1,56 @@
+require File.expand_path('../../spec_helper.rb', __FILE__)
+
+describe Dependor::MetaData do
+
+ class NoMetaDataSample
+ end
+
+ describe "for class that has no metadata specified" do
+ it "should have no dependencies" do
+ metadata = Dependor::MetaData.for(NoMetaDataSample)
+
+ metadata.dependencies.should == Set.new()
+ end
+ end
+
+ class SomeDependenciesSample
+ include Dependor::Injectable
+
+ depends_on :foo, :bar
+ end
+
+ describe "for a typical class with some dependencies" do
+ it "should contain all of the dependencies" do
+ metadata = Dependor::MetaData.for(SomeDependenciesSample)
+
+ metadata.dependencies.should == Set.new([:foo, :bar])
+ end
+ end
+
+ class InheritingFromClassWithDependenciesSample < SomeDependenciesSample
+ depends_on :baz
+ end
+
+ describe "for a class inherinting from another class with dependencies" do
+ it "should contain all of the inherited and newly declared dependencies" do
+ metadata = Dependor::MetaData.for(InheritingFromClassWithDependenciesSample)
+
+ metadata.dependencies.should == Set.new([:foo, :bar, :baz])
+ end
+ end
+
+ class InheritingFromClassWithNoDependenciesSample < NoMetaDataSample
+ include Dependor::Injectable
+
+ depends_on :bar
+ end
+
+ describe "for a class inheriting from another class without dependencies" do
+ it "should contain the declared dependencies" do
+ metadata = Dependor::MetaData.for(InheritingFromClassWithNoDependenciesSample)
+
+ metadata.dependencies.should == Set.new([:bar])
+ end
+ end
+
+end
@@ -0,0 +1,10 @@
+$:.push File.expand_path("../../lib", __FILE__)
+
+require 'rubygems'
+require 'rspec'
+
+require 'dependor'
+
+RSpec.configure do |c|
+ c.color_enabled = true
+end

0 comments on commit 66e4db3

Please sign in to comment.