diff --git a/lib/fog/bin/rackspace.rb b/lib/fog/bin/rackspace.rb
index 30352a1c8..af0797184 100644
--- a/lib/fog/bin/rackspace.rb
+++ b/lib/fog/bin/rackspace.rb
@@ -8,6 +8,8 @@ class Rackspace < Fog::Bin
Fog::Rackspace::BlockStorage
when :cdn
Fog::CDN::Rackspace
+ when :cdn_v2
+ Fog::Rackspace::CDNV2
when :compute
Fog::Compute::Rackspace
when :compute_v2
@@ -43,6 +45,8 @@ class Rackspace < Fog::Bin
when :cdn
Fog::Logger.warning("Rackspace[:cdn] is not recommended, use CDN[:rackspace] for portability")
Fog::CDN.new(:provider => 'Rackspace')
+ when :cdn_v2
+ Fog::Rackspace::CDNV2.new
when :compute
Fog::Logger.warning("Rackspace[:compute] is not recommended, use Compute[:rackspace] for portability")
Fog::Compute.new(:provider => 'Rackspace')
diff --git a/lib/fog/rackspace.rb b/lib/fog/rackspace.rb
index bf189e331..c7154e53e 100644
--- a/lib/fog/rackspace.rb
+++ b/lib/fog/rackspace.rb
@@ -1,6 +1,7 @@
require 'fog/rackspace/auto_scale'
require 'fog/rackspace/block_storage'
require 'fog/rackspace/cdn'
+require 'fog/rackspace/cdn_v2'
require 'fog/rackspace/compute'
require 'fog/rackspace/compute_v2'
require 'fog/rackspace/databases'
diff --git a/lib/fog/rackspace/cdn_v2.rb b/lib/fog/rackspace/cdn_v2.rb
new file mode 100644
index 000000000..49f3c0bce
--- /dev/null
+++ b/lib/fog/rackspace/cdn_v2.rb
@@ -0,0 +1,141 @@
+require 'fog/rackspace/core'
+
+module Fog
+ module Rackspace
+ class CDNV2 < Fog::Service
+ requires :rackspace_api_key, :rackspace_username
+ recognizes :rackspace_auth_url, :persistent, :rackspace_cdn_ssl, :rackspace_region, :rackspace_cdn_url
+
+ PREVIEW_API_URL = "preview.cdn.api.rackspacecloud.com"
+
+ model_path 'fog/rackspace/models/cdn_v2'
+ model :service
+ collection :services
+
+ model :flavor
+ collection :flavors
+
+ request_path 'fog/rackspace/requests/cdn_v2'
+ request :create_service
+ request :delete_assets
+ request :delete_service
+ request :get_flavor
+ request :get_home_document
+ request :get_ping
+ request :get_service
+ request :list_flavors
+ request :list_services
+ request :update_service
+
+ class ServiceError < Fog::Rackspace::Errors::ServiceError; end
+ class InternalServerError < Fog::Rackspace::Errors::InternalServerError; end
+ class BadRequest < Fog::Rackspace::Errors::BadRequest; end
+
+ class Mock < Fog::Rackspace::Service
+ include Fog::Rackspace::MockData
+
+ def initialize(options)
+ @rackspace_api_key = options[:rackspace_api_key]
+ end
+
+ def request(params)
+ Fog::Mock.not_implemented
+ end
+
+ def response(params={})
+ body = params[:body] || {}
+ status = params[:status] || 200
+ headers = params[:headers] || {}
+
+ response = Excon::Response.new(:body => body, :headers => headers, :status => status)
+ if params.key?(:expects) && ![*params[:expects]].include?(response.status)
+ raise(Excon::Errors.status_error(params, response))
+ else response
+ end
+ end
+ end
+
+ class Real < Fog::Rackspace::Service
+ def initialize(options = {})
+ @rackspace_api_key = options[:rackspace_api_key]
+ @rackspace_username = options[:rackspace_username]
+ @rackspace_auth_url = options[:rackspace_auth_url]
+ @rackspace_must_reauthenticate = false
+ @connection_options = options[:connection_options] || {}
+
+ authenticate
+
+ @persistent = options[:persistent] || false
+ @connection = Fog::Core::Connection.new(endpoint_uri.to_s, @persistent, @connection_options)
+ end
+
+ def request(params, parse_json = true)
+ # TODO: This MUST be removed when CDNV2 is live
+ rewrite_cdn_v2_host!
+ # TODO: This MUST be removed when CDNV2 is live
+
+ super
+ rescue Excon::Errors::NotFound => error
+ raise NotFound.slurp(error, self)
+ rescue Excon::Errors::BadRequest => error
+ raise BadRequest.slurp(error, self)
+ rescue Excon::Errors::InternalServerError => error
+ raise InternalServerError.slurp(error, self)
+ rescue Excon::Errors::HTTPStatusError => error
+ raise ServiceError.slurp(error, self)
+ end
+
+ # TODO: This MUST be removed when CDNV2 is live
+ def rewrite_cdn_v2_host!
+ conn = @connection.instance_variable_get("@excon")
+ conn.data[:host] = PREVIEW_API_URL
+ conn.instance_variable_set("@socket_key", PREVIEW_API_URL)
+
+ if conn.data.has_key?(:__construction_args)
+ conn.data[:__construction_args][:host] = PREVIEW_API_URL
+ end
+ end
+ # TODO: This MUST be removed when CDNV2 is live
+
+ def request_uri(path, options={})
+ return path if options == {}
+ require "addressable/uri"
+ Addressable::URI.new({:path=>path, :query_values=>options}).request_uri
+ end
+
+ def ping
+ self.get_ping.status == 204
+ end
+
+ def home_document
+ self.get_home_document.body
+ end
+
+ def authenticate(options={})
+ super({
+ :rackspace_api_key => @rackspace_api_key,
+ :rackspace_username => @rackspace_username,
+ :rackspace_auth_url => @rackspace_auth_url,
+ :connection_options => @connection_options
+ })
+ end
+
+ def service_name
+ :rackCDN
+ end
+
+ def request_id_header
+ "x-raxcdn-id"
+ end
+
+ def region
+ @rackspace_region
+ end
+
+ def endpoint_uri(service_endpoint_url=nil)
+ @uri = super(@rackspace_endpoint || service_endpoint_url)
+ end
+ end
+ end
+ end
+end
diff --git a/lib/fog/rackspace/core.rb b/lib/fog/rackspace/core.rb
index 7a91314e1..3e44781c7 100644
--- a/lib/fog/rackspace/core.rb
+++ b/lib/fog/rackspace/core.rb
@@ -88,6 +88,7 @@ module Fog
service(:auto_scale, 'AutoScale')
service(:block_storage, 'BlockStorage')
service(:cdn, 'CDN')
+ service(:cdn_v2, 'CDN v2')
service(:compute, 'Compute')
service(:compute_v2, 'Compute v2')
service(:dns, 'DNS')
diff --git a/lib/fog/rackspace/docs/cdn_v2.md b/lib/fog/rackspace/docs/cdn_v2.md
new file mode 100644
index 000000000..0c8fd7adf
--- /dev/null
+++ b/lib/fog/rackspace/docs/cdn_v2.md
@@ -0,0 +1,351 @@
+#Rackspace CDNV2
+
+This document explains how to get started using CDNV2 with Fog. It assumes you have read the [Getting Started with Fog and the Rackspace Open Cloud](getting_started.md) document.
+
+## Starting irb console
+
+Start by executing the following command:
+
+ irb
+
+Once `irb` has launched you need to require the Fog library.
+
+If using Ruby 1.8.x execute:
+
+ require 'rubygems'
+ require 'fog'
+
+If using Ruby 1.9.x execute:
+
+ require 'fog'
+
+## Create Service
+
+Next, create a connection to Rackspace's CDNV2 API:
+
+Using a US-based account:
+
+ service = Fog::Rackspace::CDNV2.new({
+ :rackspace_username => RACKSPACE_USER_NAME, # Your Rackspace Username
+ :rackspace_api_key => RACKSPACE_API, # Your Rackspace API key
+ :rackspace_region => :ord, # Defaults to :dfw
+ })
+
+Using a UK-based account:
+
+ service = Fog::Compute.new({
+ :rackspace_username => RACKSPACE_USER_NAME, # Your Rackspace Username
+ :rackspace_api_key => RACKSPACE_API, # Your Rackspace API key
+ :rackspace_auth_url => Fog::Rackspace::UK_AUTH_ENDPOINT,
+ :rackspace_region => :lon,
+ })
+
+To learn more about obtaining cloud credentials refer to the [Getting Started with Fog and the Rackspace Open Cloud](getting_started.md) document.
+
+By default `Fog::Rackspace::CDNV2` will authenticate against the US authentication endpoint and connect to the DFW region. You can specify alternative authentication endpoints using the key `:rackspace_auth_url`. Please refer to [Alternate Authentication Endpoints](http://docs.rackspace.com/auth/api/v2.0/auth-client-devguide/content/Endpoints-d1e180.html) for a list of alternative Rackspace authentication endpoints.
+
+Alternative regions are specified using the key `:rackspace_region `. A list of regions available for Cloud Servers can be found by executing the following:
+
+ identity_service = Fog::Identity({
+ :provider => 'Rackspace', # Rackspace Fog provider
+ :rackspace_username => RACKSPACE_USER_NAME, # Your Rackspace Username
+ :rackspace_api_key => RACKSPACE_API, # Your Rackspace API key
+ :rackspace_auth_url => Fog::Rackspace::UK_AUTH_ENDPOINT # Not specified for US Cloud
+ })
+
+ identity_service.service_catalog.display_service_regions :cloudServersOpenStack
+
+### Optional Connection Parameters
+
+Fog supports passing additional connection parameters to its underlying HTTP library (Excon) using the `:connection_options` parameter.
+
+
+
+ Key |
+ Description |
+
+
+ :connect_timeout |
+ Connection timeout (default: 60 seconds) |
+
+
+ :read_timeout |
+ Read timeout for connection (default: 60 seconds) |
+
+ :write_timeout |
+ Write timeout for connection (default: 60 seconds) |
+
+
+ :proxy |
+ Proxy for HTTP and HTTPS connections |
+
+
+ :ssl_ca_path |
+ Path to SSL certificate authorities |
+
+
+ :ssl_ca_file |
+ SSL certificate authority file |
+
+
+ :ssl_verify_peer |
+ SSL verify peer (default: true) |
+
+
+
+
+## Fog Abstractions
+
+Fog provides both a **model** and **request** abstraction. The request abstraction provides the most efficient interface and the model abstraction wraps the request abstraction to provide a convenient `ActiveModel` like interface.
+
+### Request Layer
+
+The request abstraction maps directly to the [CDNV2 API](http://docs.rackspace.com/networks/api/v2/cn-devguide/content/ch_overview.html). It provides the most efficient interface to the Rackspace CDNV2
+
+To see a list of requests supported by the service:
+
+ service.requests
+
+This returns:
+
+ [:create_service, :delete_assets, :delete_service, :get_flavor, :get_home_document, :get_ping, :get_service, :list_flavors, :list_services, :update_service]
+
+#### Example Request
+
+To request a list of services:
+
+ response = service.list_services
+
+This returns in the following `Excon::Response`:
+
+ #{"services"=>[{"name"=>"SomethingDifferent.net", "domains"=>[{"domain"=>"google.com", "protocol"=>"http"}], "origins"=>[{"origin"=>"google.com", "port"=>80, "ssl"=>false, "rules"=>[]}], "restrictions"=>[], "caching"=>[], "status"=>"create_in_progress", "flavor_id"=>"cdn", "errors"=>[]
+
+To view the status of the response:
+
+ response.status
+
+**Note**: Fog is aware of valid HTTP response statuses for each request type. If an unexpected HTTP response status occurs, Fog will raise an exception.
+
+To view response body:
+
+ response.body
+
+This will return:
+
+ {"services"=>[{"name"=>"SomethingDifferent.net", "domains"=>[{"domain"=>"google.com",...
+
+
+To learn more about CDNV2 request methods refer to [rdoc](http://www.rubydoc.info/gems/fog/Fog/Rackspace/CDNV2/Real). To learn more about Excon refer to [Excon GitHub repo](https://github.com/geemus/excon).
+
+### Model Layer
+
+Fog models behave in a manner similar to `ActiveModel`. Models will generally respond to `create`, `save`, `persisted?`, `destroy`, `reload` and `attributes` methods. Additionally, fog will automatically create attribute accessors.
+
+Here is a summary of common model methods:
+
+
+
+ Method |
+ Description |
+
+
+ create |
+
+ Accepts hash of attributes and creates object.
+ Note: creation is a non-blocking call and you will be required to wait for a valid state before using resulting object.
+ |
+
+
+ save |
+ Saves object.
+ Note: not all objects support updating object. |
+
+
+ persisted? |
+ Returns true if the object has been persisted. |
+
+
+ destroy |
+
+ Destroys object.
+ Note: this is a non-blocking call and object deletion might not be instantaneous.
+ |
+
+ reload |
+ Updates object with latest state from service. |
+
+ ready? |
+ Returns true if object is in a ready state and able to perform actions. This method will raise an exception if object is in an error state. |
+
+
+ attributes |
+ Returns a hash containing the list of model attributes and values. |
+
+ identity |
+
+ Returns the identity of the object.
+ Note: This might not always be equal to object.id.
+ |
+
+
+ wait_for |
+ This method periodically reloads model and then yields to specified block until block returns true or a timeout occurs. |
+
+
+
+The remainder of this document details the model abstraction.
+
+## List Services
+
+To retrieve a list of available services:
+
+ service.services
+
+This returns a collection of `Fog::Rackspace::CDNV2::Service` models:
+
+ "google.com", "protocol"=>"http"}],
+ origins=[{"origin"=>"google.com", "port"=>80, "ssl"=>false, "rules"=>[]}],
+ caching=[],
+ restrictions=[],
+ flavor_id="cdn",
+ status="create_in_progress",
+ links=[{"href"=>"", "rel"=>"self"}, {"href"=>"...", "rel"=>"flavor"}]
+ ...
+
+
+## Create Service
+
+Create a service:
+
+ s = service.services.new
+ s.name = "work.com"
+ s.flavor_id = "cdn"
+ s.add_domain "google.com"
+ s.add_origin "google.com"
+ s.save
+
+## Update Service
+You may add, remove, or update. -- **DOCS NEEDED** --
+
+ s = service.services.first
+ s.add_operation({
+ op: "add",
+ path: "/domains/0",
+ value: {
+ origin: "cdn.somewhere.org",
+ port: 80,
+ ssl: false,
+ rules: [
+ {
+ name: "Something",
+ request_url: "google.com"
+ }
+ ]
+ }
+ })
+
+ s.save
+
+## Get Service
+
+To retrieve individual service:
+
+ service.services.get "087ffeb0-462d-4f44-b24a-2914fbfb1d42"
+
+This returns an `Fog::Rackspace::CDNV2::Service` instance:
+
+ "google.com", "protocol"=>"http"}],
+ origins=[{"origin"=>"google.com", "port"=>80, "ssl"=>false, "rules"=>[]}],
+ caching=[],
+ restrictions=[],
+ flavor_id="cdn",
+ status="create_in_progress",
+ links=[{"href"=>"", "rel"=>"self"}, {"href"=>"...", "rel"=>"flavor"}]
+
+## Delete Service
+
+To delete a service:
+
+ service.destroy
+
+**Note**: The service is not immediately destroyed, but it does occur shortly there after.
+
+## Delete Service Assets
+
+To delete a service's assets (or any owned asset via url):
+
+ service.destroy_assets(url: "/")
+
+**Note**: The service's asset is not immediately destroyed, but it does occur shortly there after.
+
+
+## List Flavors
+
+To retrieve a list of available flavors:
+
+ service.flavors
+
+This returns a collection of `Fog::Rackspace::CDNV2::Flavor` models:
+
+ "akamai", "links"=>[{"href"=>"http://www.akamai.com", "rel"=>"provider_url"}]}],
+ links=[{"href"=>"...", "rel"=>"self"}]
+ >
+ ]
+ >
+
+## Get Flavor
+
+To retrieve individual flavor:
+
+ service.flavors.get "cdn"
+
+This returns an `Fog::Rackspace::CDNV2::Flavor` instance:
+
+ "akamai", "links"=>[{"href"=>"http://www.akamai.com", "rel"=>"provider_url"}]}],
+ links=[{"href"=>"...", "rel"=>"self"}]
+ >
+
+## Ping
+
+To ping the CDN:
+
+ service.ping
+
+This returns an boolean based on successful ping.
+
+## Get Home Document
+
+To retrieve the home document:
+
+ service.home_document
+
+This returns a JSON blob that describes the home document.
+
+## Additional Resources
+
+* [fog.io](http://fog.io/)
+* [Fog rdoc](http://rubydoc.info/gems/fog/)
+* [Fog Github repo](https://github.com/fog/fog)
+* [Fog Github Issues](https://github.com/fog/fog/issues)
+* [Excon Github repo](https://github.com/geemus/excon)
+* [Rackspace Networking API](http://docs.rackspace.com/networking/api/v2/cs-devguide/content/ch_preface.html)
+
+## Support and Feedback
+
+Your feedback is appreciated! If you have specific issues with the **fog** SDK, you should file an [issue via Github](https://github.com/fog/fog/issues).
+
+For general feedback and support requests, send an email to: .
diff --git a/lib/fog/rackspace/models/cdn_v2/flavor.rb b/lib/fog/rackspace/models/cdn_v2/flavor.rb
new file mode 100644
index 000000000..1ee54c3f2
--- /dev/null
+++ b/lib/fog/rackspace/models/cdn_v2/flavor.rb
@@ -0,0 +1,14 @@
+require 'fog/core/model'
+
+module Fog
+ module Rackspace
+ class CDNV2 < Fog::Service
+ class Flavor < Fog::Model
+ identity :id
+
+ attribute :providers
+ attribute :links
+ end
+ end
+ end
+end
diff --git a/lib/fog/rackspace/models/cdn_v2/flavors.rb b/lib/fog/rackspace/models/cdn_v2/flavors.rb
new file mode 100644
index 000000000..f6711097d
--- /dev/null
+++ b/lib/fog/rackspace/models/cdn_v2/flavors.rb
@@ -0,0 +1,24 @@
+require 'fog/core/collection'
+require 'fog/rackspace/models/cdn_v2/flavor'
+
+module Fog
+ module Rackspace
+ class CDNV2 < Fog::Service
+ class Flavors < Fog::Collection
+ model Fog::Rackspace::CDNV2::Flavor
+
+ def all
+ data = service.list_flavors.body['flavors']
+ load(data)
+ end
+
+ def get(name)
+ data = service.get_flavor(name).body
+ new(data)
+ rescue Fog::Rackspace::CDNV2::NotFound
+ nil
+ end
+ end
+ end
+ end
+end
diff --git a/lib/fog/rackspace/models/cdn_v2/service.rb b/lib/fog/rackspace/models/cdn_v2/service.rb
new file mode 100644
index 000000000..f5945bb7d
--- /dev/null
+++ b/lib/fog/rackspace/models/cdn_v2/service.rb
@@ -0,0 +1,66 @@
+require 'fog/core/model'
+
+module Fog
+ module Rackspace
+ class CDNV2 < Fog::Service
+ class Service < Fog::Model
+
+ attr_accessor :operations
+
+ UUID_REGEX = /[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}/
+
+ identity :id
+
+ attribute :name
+ attribute :domains
+ attribute :origins
+ attribute :caching
+ attribute :restrictions
+ attribute :flavor_id
+ attribute :status
+ attribute :links
+
+ def initialize(options={})
+ self.operations = []
+ super
+ end
+
+ def add_domain(domain, options={})
+ self.domains ||= []
+ self.domains << {domain: domain}.merge(options)
+ self.domains
+ end
+
+ def add_origin(origin, options={})
+ self.origins ||= []
+ self.origins << {origin: origin}.merge(options)
+ self.origins
+ end
+
+ def add_operation(options={})
+ self.operations << options
+ end
+
+ def save
+ if id.nil?
+ data = service.create_service(self)
+ loc = data.headers["Location"]
+ id = UUID_REGEX.match(loc)[0]
+ merge_attributes(id: id)
+ else
+ service.update_service(self)
+ end
+ end
+
+ def destroy
+ service.delete_service(self)
+ end
+
+ def destroy_assets(options={})
+ service.delete_assets(self, options)
+ end
+
+ end
+ end
+ end
+end
diff --git a/lib/fog/rackspace/models/cdn_v2/services.rb b/lib/fog/rackspace/models/cdn_v2/services.rb
new file mode 100644
index 000000000..b95962914
--- /dev/null
+++ b/lib/fog/rackspace/models/cdn_v2/services.rb
@@ -0,0 +1,24 @@
+require 'fog/core/collection'
+require 'fog/rackspace/models/cdn_v2/service'
+
+module Fog
+ module Rackspace
+ class CDNV2 < Fog::Service
+ class Services < Fog::Collection
+ model Fog::Rackspace::CDNV2::Service
+
+ def all(options={})
+ data = service.list_services(options).body['services']
+ load(data)
+ end
+
+ def get(id)
+ data = service.get_service(id).body
+ new(data)
+ rescue Fog::Rackspace::CDNV2::NotFound
+ nil
+ end
+ end
+ end
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/create_service.rb b/lib/fog/rackspace/requests/cdn_v2/create_service.rb
new file mode 100644
index 000000000..3bf539632
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/create_service.rb
@@ -0,0 +1,10 @@
+class Fog::Rackspace::CDNV2::Real
+ def create_service(service)
+ request(
+ :expects => [201, 202],
+ :method => 'POST',
+ :body => Fog::JSON.encode(service),
+ :path => "services"
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/delete_assets.rb b/lib/fog/rackspace/requests/cdn_v2/delete_assets.rb
new file mode 100644
index 000000000..0a318a390
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/delete_assets.rb
@@ -0,0 +1,12 @@
+class Fog::Rackspace::CDNV2::Real
+ def delete_assets(service, options={})
+ uri = request_uri("services/#{service.id}/assets", options)
+
+ request(
+ :expects => 202,
+ :method => 'DELETE',
+ :path => uri,
+ :headers => { :accept => "*/*" }
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/delete_service.rb b/lib/fog/rackspace/requests/cdn_v2/delete_service.rb
new file mode 100644
index 000000000..5803b6285
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/delete_service.rb
@@ -0,0 +1,9 @@
+class Fog::Rackspace::CDNV2::Real
+ def delete_service(service)
+ request(
+ :expects => 202,
+ :method => 'DELETE',
+ :path => "services/#{service.id}"
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/get_flavor.rb b/lib/fog/rackspace/requests/cdn_v2/get_flavor.rb
new file mode 100644
index 000000000..26b8a794d
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/get_flavor.rb
@@ -0,0 +1,9 @@
+class Fog::Rackspace::CDNV2::Real
+ def get_flavor(id)
+ request(
+ :expects => [200],
+ :method => 'GET',
+ :path => "flavors/#{id}"
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/get_home_document.rb b/lib/fog/rackspace/requests/cdn_v2/get_home_document.rb
new file mode 100644
index 000000000..266cb03d3
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/get_home_document.rb
@@ -0,0 +1,9 @@
+class Fog::Rackspace::CDNV2::Real
+ def get_home_document
+ request(
+ :expects => [200],
+ :method => 'GET',
+ :path => ""
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/get_ping.rb b/lib/fog/rackspace/requests/cdn_v2/get_ping.rb
new file mode 100644
index 000000000..8ac4efa1b
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/get_ping.rb
@@ -0,0 +1,10 @@
+class Fog::Rackspace::CDNV2::Real
+ def get_ping
+ request(
+ :expects => [204],
+ :method => 'GET',
+ :path => "ping",
+ :headers => { :accept => "*/*" }
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/get_service.rb b/lib/fog/rackspace/requests/cdn_v2/get_service.rb
new file mode 100644
index 000000000..bbfcb468f
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/get_service.rb
@@ -0,0 +1,9 @@
+class Fog::Rackspace::CDNV2::Real
+ def get_service(id)
+ request(
+ :expects => 200,
+ :method => 'GET',
+ :path => "services/#{id}"
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/list_flavors.rb b/lib/fog/rackspace/requests/cdn_v2/list_flavors.rb
new file mode 100644
index 000000000..cda76ce07
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/list_flavors.rb
@@ -0,0 +1,9 @@
+class Fog::Rackspace::CDNV2::Real
+ def list_flavors
+ request(
+ :expects => [200],
+ :method => 'GET',
+ :path => "flavors"
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/list_services.rb b/lib/fog/rackspace/requests/cdn_v2/list_services.rb
new file mode 100644
index 000000000..8bb7a4c40
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/list_services.rb
@@ -0,0 +1,9 @@
+class Fog::Rackspace::CDNV2::Real
+ def list_services(options={})
+ request(
+ :expects => [200],
+ :method => 'GET',
+ :path => request_uri("services", options)
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/cdn_v2/update_service.rb b/lib/fog/rackspace/requests/cdn_v2/update_service.rb
new file mode 100644
index 000000000..22480127a
--- /dev/null
+++ b/lib/fog/rackspace/requests/cdn_v2/update_service.rb
@@ -0,0 +1,10 @@
+class Fog::Rackspace::CDNV2::Real
+ def update_service(service)
+ request(
+ :expects => [201, 202],
+ :method => 'PATCH',
+ :body => Fog::JSON.encode(service.operations),
+ :path => "services/#{service.id}"
+ )
+ end
+end
diff --git a/lib/fog/rackspace/requests/identity/create_token.rb b/lib/fog/rackspace/requests/identity/create_token.rb
index c1eec7342..b0672b992 100644
--- a/lib/fog/rackspace/requests/identity/create_token.rb
+++ b/lib/fog/rackspace/requests/identity/create_token.rb
@@ -96,6 +96,8 @@ module Fog
"https://storage101.#{r}#{Fog::Mock.random_numbers(1)}.clouddrive.com/v1/#{object_tenant}"
end),
+ service_catalog_entry("rackCDN", "rax:cdn", compute_tenant, :rackspace_api_version => '1.0'),
+
service_catalog_entry("cloudMonitoring", "rax:monitor", compute_tenant,
:single_endpoint => true, :rackspace_api_name => 'monitoring'),