Designing HTTP Interfaces and RESTful Web Services (PHPBNL11 2011-01-28)
A Guide to Designing and Building RESTful Web Services With WCF 3
-
Upload
kailas-lokhande -
Category
Documents
-
view
8 -
download
0
description
Transcript of A Guide to Designing and Building RESTful Web Services With WCF 3
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 1/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 2/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 3/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 4/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 5/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 6/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 7/54
?tag={tag}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 8/54
{username}?tag={tag}
/users/{username}
/users/{username}/profile
/users/{username}/bookmarks
/users/{username}/bookmarks?tag={tag}
/users/{username}/bookmarks/{id}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 9/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 10/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 11/54
Authorization: skonnard:uCMfSzkjue+HSDygYB5aEg==
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 12/54
<User>
<Email>[email protected]</Email>
<Name>Aaron Skonnard</Name>
</User>
<User>
<Bookmarks>http://contoso.com/bookmarkservice/skonnard</Bookmarks>
<Email>[email protected]</Email>
<Id>http://contoso.com/bookmarkservice/skonnard</Id>
<Name>Aaron Skonnard</Name>
</User>
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 13/54
<UserProfile>
<Bookmarks>http://contoso.com/bookmarkservice/skonnard</Bookmarks>
<Id>http://contoso.com/bookmarkservice/skonnard</Id>
<Name>Aaron Skonnard</Name>
</UserProfile>
<Bookmark>
<Public>true</Public>
<Tags>REST,WCF</Tags>
<Title>Aaron’s Blog</Title>
<Url>http://pluralsight.com/aaron</Url>
</Bookmark>
<Bookmark>
<Id>http://contoso.com/bookmarkservice/users/skonnard/bookmarks/13</Id>
<LastModified>2008‐03‐12T00:00:00</LastModified>
<Public>true</Public>
<Tags>REST,WCF</Tags>
<Title>Aaron's Blog</Title>
<Url>http://pluralsight.com/aaron</Url>
<User>skonnard</User>
<UserProfile>http://contoso.com/bookmarkservice/users/skonnard/profile
</UserProfile>
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 14/54
</Bookmark>
<Bookmarks>
<Bookmark>
<Id>http://contoso.com/bookmarkservice/users/skonnard/bookmarks/13</Id>
<LastModified>2008‐03‐12T00:00:00</LastModified>
<Public>true</Public>
<Tags>REST,WCF</Tags>
<Title>Aaron's Blog</Title>
<Url>http://pluralsight.com/aaron</Url>
<User>skonnard</User>
<UserProfile>http://contoso.com/bookmarkservice/users/skonnard/profile
</UserProfile>
</Bookmark>
<Bookmark>...</Bookmark>
<Bookmark>...</Bookmark>
</Bookmarks>
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 15/54
?tag={tag}&format=json
{username}?tag={tag}&format=json
users/{username}?format=json
users/{username}/profile?format=json
...
{User:{Email:'[email protected]', Name:'Aaron Skonnard'}}
feed?tag={tag}&format={format}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 16/54
<feed xmlns="http://www.w3.org/2005/Atom">
<title>Public Bookmarks</title>
<updated>2008‐09‐13T18:30:02Z</updated>
<id>http://contoso.com/bookmarkservice/feed</id>
<entry>
<author>
<name>Aaron Skonnard</name>
</author>
<title>Aaron’s Blog</title>
<link href="http://pluralsight.com/aaron"/>
<id>http://contoso.com/bookmarkservice/users/skonnard/bookmarks/13</id>
<updated>2008‐09‐13T18:30:02Z</updated>
<category term="REST,WCF"/>
</entry>
<entry>...</entry>
<entry>...</entry>
</feed>
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 17/54
<service xmlns="http://www.w3.org/2007/app"
xmlns:atom="http://www.w3.org/2005/Atom">
<workspace>
<atom:title>Contoso Bookmark Service</atom:title>
<collection href="http://contoso.com/bookmarkservice/" >
<atom:title>Public Bookmarks</atom:title>
</collection>
<collection href="http://contoso.com/bookmarkservice/skonnard" >
<atom:title>Aaron Skonnard's Public Bookmarks</atom:title>
</collection>
<collection>...</collection>
</workspace>
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 18/54
</service>
OPTIONS http://contoso.com/bookmarkservice/skonnard/bookmarks HTTP/1.1
HTTP/1.1 200 OK
Allow: GET, POST
HTTP/1.1 200 OK
Allow: GET
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 19/54
POST /bookmarkservice/skonnard/bookmarks/123 HTTP/1.1
X‐HTTP‐Method‐Override: DELETE
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 20/54
public class BookmarkService : IHttpHandler
{
public bool IsReusable { get { return true; } }
public void ProcessRequest(HttpContext context)
{
Uri uri = context.Request.Url;
// compare URI to resource templates and find match
if (Matches(uri, "{username}?tag={tag}"))
{
// extract variables from URI
Dictionary<string, string> vars =
ExtractVariables(uri, "{username}?tag={tag} ");
string username = vars["username"];
string tag = vars["tag"];
// figure out which HTTP method is being used
switch (context.Request.HttpMethod)
{
// dispatch to internal methods based on URI and HTTP method
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 21/54
// and write the correct response status & entity body
case "GET":
List<Bookmark> bookmarks = GetBookmarks(username, tag);
WriteBookmarksToResponse(context.Response, bookmarks);
SetResponseStatus(context.Response, "200", "OK");
break;
case "POST":
Bookmark newBookmark = ReadBookmarkFromRequest(context.Request);
string id = CreateNewBookmark(username, newBookmark);
WriteLocationHeader(id);
SetResponseStatus(context.Response, "201", "Created");
break;
default:
SetResponseStatus(context.Response, "405", "Method Not Allowed");
}
}
if (Matches(uri, "users/{username}/bookmarks/{id}"))
{
// dispatch to internal methods based on URI and HTTP method
// and write the correct response status & entity body
... }
... // match addition URI templates here
}
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 22/54
public class User
{
public Uri Id { get; set; }
public string Username { get; set; }
public string Name { get; set; }
public string Email { get; set; }
public Uri Bookmarks { get; set; }
}
public class UserProfile{
public Uri Id { get; set; }
public string Name { get; set; }
public Uri Bookmarks { get; set; }
}
public class Bookmark
{
public Uri Id { get; set; }
public string Title { get; set; }
public Uri Url { get; set; }
public string User { get; set; } public Uri UserLink { get; set; }
public string Tags { get; set; }
public bool Public { get; set; }
public DateTime LastModified { get; set; }
}
[CollectionDataContract]
public class Bookmarks : List<Bookmark>
{
public Bookmarks() { }
public Bookmarks(List<Bookmark> bookmarks) : base(bookmarks) {}
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 23/54
public class BookmarkService
{
Bookmarks GetPublicBookmarks(string tag) {...}
Bookmarks GetUserPublicBookmarks(string username, string tag) {...}
Bookmarks GetUserBookmarks(string username) {...}
UserProfile GetUserProfile(string username) {...} User GetUser(string username) {...}
void PutUser(string username, User user) {...}
void DeleteUser(string username) {...}
Bookmark GetBookmark(string username, string id) {...}
void PostBookmark(string username, Bookmark newValue) {...}
void PutBookmark(string username, string id, Bookmark bm) {...}
void DeleteBookmark(string username, string id) {...}
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 24/54
Uri baseUri = new Uri("http://contoso.com/bookmarkservice");
UriTemplate uriTemplate = new UriTemplate(
"users/{username}/bookmarks/{id}");
// generate a new bookmark URI
Uri newBookmarkUri = uriTemplate.BindByPosition(baseUri, "skonnard", "123");// match an existing bookmark URI
UriTemplateMatch match = uriTemplate.Match(baseUri, newBookmarkUri);
System.Diagnostics.Debug.Assert(match != null);
Console.WriteLine(match.BoundVariables["username"]);
Console.WriteLine(match.BoundVariables["id"]);
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 25/54
[ServiceContract]
public partial class BookmarkService
{ [WebGet(UriTemplate = "?tag={tag}")]
[OperationContract]
Bookmarks GetPublicBookmarks(string tag) {...}
[WebGet(UriTemplate = "{username}?tag={tag}")]
[OperationContract]
Bookmarks GetUserPublicBookmarks(string username, string tag) {...}
[WebGet(UriTemplate = "users/{username}/bookmarks?tag={tag}")]
[OperationContract]
Bookmarks GetUserBookmarks(string username, string tag) {...}
[WebGet(UriTemplate = "users/{username}/profile")]
[OperationContract]
UserProfile GetUserProfile(string username) {...}
[WebGet(UriTemplate = "users/{username}")]
[OperationContract]
User GetUser(string username) {...}
[WebGet(UriTemplate = "users/{username}/bookmarks/{bookmark_id}" )]
[OperationContract]
Bookmark GetBookmark(string username, string bookmark_id) {...}
...
}
[ServiceContract]
public partial class BookmarkService
{
[WebInvoke(Method = "PUT", UriTemplate = "users/{username}")]
[OperationContract]
void PutUserAccount(string username, User user) {...}
[WebInvoke(Method = "DELETE", UriTemplate = "users/{username}")]
[OperationContract]
void DeleteUserAccount(string username) {...}
[WebInvoke(Method = "POST", UriTemplate = "users/{username}/bookmarks")]
[OperationContract]
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 26/54
void PostBookmark(string username, Bookmark newValue) {...}
[WebInvoke(Method = "PUT", UriTemplate = "users/{username}/bookmarks/{id")]
[OperationContract]
void PutBookmark(string username, string id, Bookmark bm) {...}
[WebInvoke(Method = "DELETE", UriTemplate = "users/{username}/bookmarks/{id}")]
[OperationContract]
void DeleteBookmark(string username, string id) {...}
...
}
[ServiceContract]
public partial class BookmarkService
{
// in‐memory resource collections
Dictionary<string, User> users = new Dictionary<string, User>();
Dictionary<string, Bookmark> bookmarks = new Dictionary<string, Bookmark>();
[WebGet(UriTemplate = "users/{username}")]
[OperationContract]
User GetUserAccount(string username)
{
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 27/54
if (!IsUserAuthorized(username))
{
WebOperationContext.Current.OutgoingResponse.StatusCode =
HttpStatusCode.Unauthorized;
return;
}
User user = FindUser(username);
if (user == null)
{
WebOperationContext.Current.OutgoingResponse.SetStatusAsNotFound();
return null;
}
return user;
}
[WebInvoke(Method = "PUT", UriTemplate = "users/{username}")]
[OperationContract]
void PutUserAccount(string username, User newValue)
{
User user = FindUser(username);
if (user == null)
{ // set status to created and include new URI in Location header
WebOperationContext.Current.OutgoingResponse.SetStatusAsCreated(
GetUserLink(username));
... // process new user backend logic
}
else if (!IsUserAuthorized(username))
{
WebOperationContext.Current.OutgoingResponse.StatusCode =
HttpStatusCode.Unauthorized;
return;
} // create or update new user, but don't let user set Id/Bookmarks
newValue.Id = GetUserLink(username);
newValue.Bookmarks = GetUserBookmarksLink(username);
users[username] = newValue;
}
... // remaining methods ommitted
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 28/54
ServiceHost host = new ServiceHost(typeof(BookmarkService),
new Uri("http://localhost:8080/bookmarkservice"));
host.Open();
... // keep the host open until you want to shut it down
WebServiceHost host = new WebServiceHost(typeof(BookmarkService),
new Uri("http://localhost:8080/bookmarkservice"));
host.Open();
... // keep the host open until you want to shut it down
<configuration>
<system.serviceModel>
<services> <service name="BookmarkService">
<endpoint binding="webHttpBinding" contract="BookmarkService"
behaviorConfiguration="webHttp"/>
</service>
</services>
<behaviors>
<endpointBehaviors>
<behavior name="webHttp">
<webHttp/>
</behavior>
</endpointBehaviors> </behaviors>
</system.serviceModel>
<configuration>
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 29/54
<%@ ServiceHost Service="BookmarkService"
Factory="System.ServiceModel.Activation.WebServiceHostFactory"%>
<configuration>
<system.serviceModel>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true"/>
</system.serviceModel>
</configuration>
[AspNetCompatibilityRequirements(RequirementsMode =
AspNetCompatibilityRequirementsMode.Allowed)]
[ServiceContract]
public partial class BookmarkService
{
...
http://localhost/bookmarkservice.svc/skonnard?tag=wcf
http://localhost/bookmarkservice.svc/users/skonnard/bookmarks/13
...
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 30/54
http://localhost/bookmarkservice/skonnard?tag=wcf
http://localhost/bookmarkservice/users/skonnard/bookmarks/13
...
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 31/54
[ServiceContract]public partial class BookmarkService
{
...
[WebInvoke(Method = "POST", RequestFormat=WebMessageFormat.Json,
UriTemplate = "users/{username}/bookmarks?format=json")]
[OperationContract]
void PostBookmarkAsJson(string username, Bookmark newValue)
{
HandlePostBookmark(username, newValue);
}
[WebGet(ResponseFormat= WebMessageFormat.Json, UriTemplate = "users/{username}/bookmarks/{id}?format=json" )]
[OperationContract]
Bookmark GetBookmarkAsJson(string username, string id)
{
HandleGetBookmark(username, id);
}
...
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 32/54
[WebGet(UriTemplate ="feed?tag={tag}&format=atom")]
[ServiceKnownType(typeof(Rss20FeedFormatter))]
[ServiceKnownType(typeof(Atom10FeedFormatter))]
[OperationContract]
SyndicationFeedFormatter GetPublicBookmarksFeed(string tag, string format)
{
Bookmarks publicBookmarks = HandleGetPublicBookmarks(tag); WebOperationContext ctx = WebOperationContext.Current;
List<SyndicationItem> items = new List<SyndicationItem>();
foreach (Bookmark bm in publicBookmarks)
{
SyndicationItem item = new SyndicationItem(bm.Title, "", bm.Url,
bm.Id.ToString(), new DateTimeOffset(bm.LastModified));
foreach (string c in bm.Tags.Split(','))
item.Categories.Add(new SyndicationCategory(c));
item.Authors.Add(new SyndicationPerson("", bm.User, ""));
items.Add(item);
} SyndicationFeed feed = new SyndicationFeed()
{
Title = new TextSyndicationContent("Public Bookmarks"),
Id = ctx.IncomingRequest.UriTemplateMatch.RequestUri.ToString(),
LastUpdatedTime = DateTime.Now,
Items = items
};
if (format.Equals("atom"))
return new Atom10FeedFormatter(feed);
else
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 33/54
return new Rss20FeedFormatter(feed);
}
ServiceDocument HandleGetServiceDocument()
{
List<ResourceCollectionInfo> collections = new List<ResourceCollectionInfo>();
collections.Add(new ResourceCollectionInfo(
new TextSyndicationContent("Public Bookmarks"),
GetPublicBookmarksFeedLink()));
foreach (string user in users.Keys)
collections.Add(
new ResourceCollectionInfo(
new TextSyndicationContent(
string.Format("Public Bookmarks by {0}", user)),
GetUserBookmarksFeedLink(user)));
List<Workspace> workspaces = new List<Workspace>();
workspaces.Add(new Workspace(
new TextSyndicationContent("Contoso Bookmark Service"), collections));
return new ServiceDocument(workspaces);}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 34/54
if (!AuthenticateUser(username))
{
private bool AuthenticateUser(string user)
{
WebOperationContext ctx = WebOperationContext.Current;
string requestUri = ctx.IncomingRequest.UriTemplateMatch.RequestUri.ToString();
string authHeader = ctx.IncomingRequest.Headers[HttpRequestHeader.Authorization];
// if supplied hash is valid, user is authenticated
if (IsValidUserKey(authHeader, requestUri))
return true;
return false;}
public bool IsValidUserKey(string key, string uri)
{
string[] authParts = key.Split(':');
if (authParts.Length == 2)
{
string userid = authParts[0];
string hash = authParts[1];
if (ValidateHash(userid, uri, hash))
return true;
} return false;
}
bool ValidateHash(string userid, string uri, string hash)
{
if (!UserKeys.ContainsKey(userid))
return false;
string userkey = UserKeys[userid];
byte[] secretBytes = ASCIIEncoding.ASCII.GetBytes(userkey);
HMACMD5 hmac = new HMACMD5(secretBytes);
byte[] dataBytes = ASCIIEncoding.ASCII.GetBytes(uri);
byte[] computedHash = hmac.ComputeHash(dataBytes); string computedHashString = Convert.ToBase64String(computedHash);
return computedHashString.Equals(hash);
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 35/54
WebOperationContext.Current.OutgoingResponse.StatusCode =
HttpStatusCode.Unauthorized;
return;
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 36/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 37/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 38/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 39/54
public class Bookmark
{
public Uri Url { get; set; }
public string User { get; set; }
public string Title { get; set; }
public string Tags { get; set; }
public bool Public { get; set; }
public DateTime LastModified { get; set; }
}
public class BookmarkItemInfo
{
public Bookmark Bookmark { get; set; }
public Uri Link { get; set; }
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 40/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 41/54
[ServiceBehavior(IncludeExceptionDetailInFaults = true,
InstanceContextMode = InstanceContextMode.Single, ConcurrencyMode = ConcurrencyMode.Single)]
[AspNetCompatibilityRequirements(
RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
[ServiceContract]
public partial class FeedService
{
[WebGet(UriTemplate = "?numItems={i}")]
[OperationContract]
public Atom10FeedFormatter GetFeed(int i)
{
SyndicationFeed feed; // TODO: Change the sample content feed creation logic here
if (i == 0) i = 1;
// Create the list of syndication items. These correspond to Atom entries
List<SyndicationItem> items = new List<SyndicationItem>();
for (int j = 1; j <= i; ++j)
{
items.Add(new SyndicationItem()
{
// Every entry must have a stable unique URI id
Id = String.Format(
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 42/54
CultureInfo.InvariantCulture, "http://tmpuri.org/Id{0}", j),
Title = new TextSyndicationContent(
String.Format("Sample item '{0}'", j)),
// Every entry should include the last time it was updated
LastUpdatedTime = new DateTime(
2008, 7, 1, 0, 0, 0, DateTimeKind.Utc),
// The Atom spec requires an author for every entry.
Authors =
{
new SyndicationPerson()
{
Name = "Sample Author"
}
},
// The content of an Atom entry can be text, xml, a link or
// arbitrary content. In this sample text content is used.
Content = new TextSyndicationContent("Sample content"),
});
}
// create the feed containing the syndication items.
feed = new SyndicationFeed()
{
// The feed must have a unique stable URI id
Id = "http://tmpuri.org/FeedId",
Title = new TextSyndicationContent("Sample feed"),
Items = items,
Links =
{
// A feed should have a link to the service that produced the feed.
GetSelfLink(),
}
}; WebOperationContext.Current.OutgoingResponse.ContentType = AtomContentType;
return feed.GetAtom10Formatter();
}
...
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 43/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 44/54
public class BookmarksEDM : DataService< /* TODO: your data source class name */ >
{
// This method is called only once to initialize service‐wide policies.
public static void InitializeService(IDataServiceConfiguration config)
{
// TODO: set rules to indicate which entity sets are visible, updatable, etc.
// Examples:
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 45/54
// config.SetEntitySetAccessRule("MyEntityset", EntitySetRights.AllRead);
// config.SetServiceOperationAccessRule("MyServiceOperation",
// ServiceOperationRights.All);
}
}
public class BookmarksEDM : DataService<BookmarksModel.BookmarksEntities>
{
public static void InitializeService(IDataServiceConfiguration config)
{
config.SetEntitySetAccessRule("Bookmarks", EntitySetRights.All);
}
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 46/54
http://localhost:55555/BookmarksEDM.svc/Bookmarks?$filter=User%20eq%20'skonnard'
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 47/54
[DataServiceKey("Id")]
public class Bookmark
{
public string Id { get; set; }
public string Url { get; set; }
public string User { get; set; }
public string Title { get; set; }
public string Tags { get; set; }
public bool Public { get; set; }
public DateTime LastModified { get; set; }
}
// this class replaces the EDM definition ‐ it provides an in‐memory data source
public class BookmarkService
{
static List<Bookmark> bookmarks = new List<Bookmark>();
static BookmarkService()
{
... // initialize 'bookmarks' collection with a bunch of objects
}
public IQueryable<Bookmark> Bookmarks {
get { return bookmarks.AsQueryable<Bookmark>(); }
}
}
public class BookmarkDataService : DataService<BookmarkService>
{
public static void InitializeService(IDataServiceConfiguration config)
{
config.SetEntitySetAccessRule("Bookmarks", EntitySetRights.All);
}
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 48/54
if (WScript.Arguments.length < 2)
{
WScript.echo("Client HTTP Request Utility\n");
WScript.echo("usage: httprequest method uri [options]");
WScript.echo();
WScript.echo(" ‐f filename");
WScript.echo(" ‐h headerName headerValue");
WScript.Quit(1);}
var method = WScript.Arguments.Item(0);
var uri = WScript.Arguments.Item(1);
var req = new ActiveXObject("MSXML2.XMLHTTP");
var filename = null;
req.Open(method, uri, false);
WScript.echo();
WScript.echo("********* Request ********* ");
WScript.echo(method + " " + uri + " HTTP/1.1");
for (i=2; i < WScript.Arguments.length; i++)
{ var option = WScript.Arguments.Item(i);
if (option == "‐f")
filename = WScript.Arguments.Item(i+1);
if (option == "‐h")
{
WScript.echo(WScript.Arguments.Item(i+1) + ": " +
WScript.Arguments.Item(i+2));
req.setRequestHeader(WScript.Arguments.Item(i+1),
WScript.Arguments.Item(i+2));
}
}try
{
if (filename != null)
{
WScript.echo();
var fso = new ActiveXObject("Scripting.FileSystemObject");
var file = fso.OpenTextFile(filename, 1, false);
var fileContents = file.ReadAll();
file.Close();
WScript.echo(fileContents);
req.Send(fileContents);
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 49/54
static void GetPublicBookmarks()
{
string uri = "http://localhost:55555/bookmarkservice.svc/";
HttpWebRequest req = WebRequest.Create(uri) as HttpWebRequest;
HttpWebResponse resp = req.GetResponse() as HttpWebResponse;
Bookmarks bookmarks = DeserializeBookmarks(resp.GetResponseStream());
foreach (Bookmark bm in bookmarks)
Console.WriteLine("{0}\r\n{1}\r\n", bm.Title, bm.Url);
}
printResponse(req);
}
else
{
req.send();
printResponse(req);
}
}
catch(e)
{
WScript.echo();
WScript.echo("******* Response ********* ");
WScript.echo(e.message);
}
function printResponse(req)
{
WScript.echo();
WScript.echo("******* Response ********* ");
WScript.echo("HTTP/1.1" + " " + req.status + " " + req.statusText);
var headers = req.getAllResponseHeaders();
WScript.echo(headers);
WScript.echo(req.responseText);
}
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 50/54
[ServiceContract]
public interface IBookmarkService
{
[WebGet(UriTemplate = "?tag={tag}")]
[OperationContract]
Bookmarks GetPublicBookmarks(string tag);
...
}
WebChannelFactory<IBookmarkService> cf = new WebChannelFactory<IBookmarkService>( new Uri("http://localhost:55555/BookmarkService.svc" ));
IBookmarkService channel = cf.CreateChannel();
Bookmarks bms = channel.GetPublicBookmarks("WCF");
foreach (Bookmark bm in bms)
Console.WriteLine("{0}\r\n{1}", bm.Title, bm.Url);
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 51/54
BookmarkService bookmarkService = new BookmarkService(
new Uri("http://localhost:55555/Bookmarks.svc/"));
// this generates the following URL:
// http://localhost:55555/Bookmarks.svc/Bookmarks()?$filter=substringof('WCF',Tags)&// $orderby=LastModified
var bookmarks = from b in bookmarkService.Bookmarks
where b.Tags.Contains("WCF")
orderby b.LastModified
select b;
foreach (Bookmark bm in bookmarks)
Console.WriteLine("{0}\r\n{1}", bm.Title, bm.Url);
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 52/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 53/54
7/17/2019 A Guide to Designing and Building RESTful Web Services With WCF 3
http://slidepdf.com/reader/full/a-guide-to-designing-and-building-restful-web-services-with-wcf-3 54/54