RESTful Web API Design - Software-architects

Transcription

RESTful Web API DesignRainer Stropek

Software Architecture Summit 2015Rainer Stropeksoftware architects gmbhRESTfulWeb http://www.timecockpit.comMail rainer@timecockpit.comTwitter @rstropekWeb API DesignSaves the day.

AgendaRESTful Web APIs have become an integral part of modern software packages. They are important forintegration scenarios in enterprises and in the cloud. This workshop is dedicated to designing RESTfulWeb APIs. Rainer Stropek, himself founder a SaaS-focused company, will guide you through the world ofRESTful APIs. In particular, Rainer will speak about the following topics: Short recap of the basic principles of RESTful Web APIs Real-world RESTful API design (e.g. addressing in multi-tenant systems, versioning, long-runningoperations, etc.) Authentication and authorization with OAuth2 and OpenID Connect The OData standard for RESTful APIs The role of metadata using the examples of http://swagger.io/ and OData Securing and operating RESTful APIs using the example of Azure API Management Code samples using Node.js with JavaScript and .NET with C#Attendees of this workshop should have some understanding of http and cloud computing. Practicalexperience regarding RESTful API design or development is not necessary.

RESTful Web APIsShort recap of the basic principles of RESTful Web APIs

What is „REST“?Representational State Transfer (REST)Architecture style, not a standardHTTPRequest-response protocol in client-server systemsHTTP methods („verbs“)GET – retrieve data, no side effects (except logging, caching, etc.)HEAD – like get but without response body, useful to retrieve metadataPOST – submit new dataPUT – update or createPATCH – partial updateDELETETRACE – echoOPTIONS – query verbs that the server supports for a given URL

What is „REST“?HTTPIdempotent requestsGET, HEAD, OPTIONS, TRACEPUT, DELETENon idempotent requestsPOSTStatus Codes (complete list of status codes), examples:200 OK201 Created301 Moved permanently400 Bad request401 Unauthorized403 Forbidden (authorization will not help)404 Not found405 Method not allowed (wrong verb)500 Internal server errorSource of Table: Mark Massé, REST API Design Rulebook, O‘Reilly

What is „REST“?HTTPHeader fields (list of header fields), examples:Accept – e.g. application/jsonAuthorization – authentication , If-Modified-Since, If-Unmodified-SinceX- - non-standard fieldsETag – identifier for a specific version of a resourceLast-ModifiedSet-Cookie

What is „REST“?Important REST principlesStatelessNo client context stored on the server, each request is completeCacheableResponses explicitly indicate their cacheabilityLayered SystemClient cannot tell if connected directly to the server (e.g. reverse proxies)URIsResources are identified using Uniform Resource Identifiers (URIs)Resource representationXML, JSON, Atom – today mostly JSON

RESTful Web APIInteracting with a RESTfulweb apiToolsAzure Mobile ServiceFiddlerPostmanDemo

Create Azure Mobile ServiceShow REST API documentationCreate table, allow all requests anonymouslyShow POST, GET in FiddlerShow POST, PATCH, DELETE, GET in PostmanShow table content in SQL Management StudioChange access policy to API keyGet API keyShow GET with API key in X-ZUMO-APPLICATION headerRESTful Web APIDemoscript

API DesignReal-world RESTful API design

Design RulesDo use HTTPSNo-brainer on public networksRecommended on company/home network, tooDo use a consistent naming schemaPrefer hyphens (“-”) instead of underscores (“ ”) in URIsDo not mix languagesPrefer lowercase letters in URIsPrefer camel casing for resource representation (e.g. in JSON)Singular noun for documents, plural noun for collections, verb for controller names

Design RulesDo carefully model URI pathsURIs should reflect the API‘s resource modelE.g. d example: 1f8e3712dffc/ordersDon’t forget controller resourcesConsider identity values for variable URI path segmentsE.g. https://api.myservice.com/customers/ALFKI/ordersDo use HTTP verbs as they were intended toAlso for controller resources (e.g. POST for controller that creates data)Consider firewall problems with PUT and sometimes even DELETEAvoid using controller names instead of HTTP verbsBad example: ?id ALFKI

RESTful Web APIController resourcesDemo

exports.post function(request, response) {if (!request.body !request.body.rows) {response.status(400).end();}else {var customerTable request.service.tables.getTable('customers');for (var i 0; i request.body.rows; i ) {var customer {firstName: "Test " i.toString(),lastName: "Test " i.toString(),revenueYTD: i * tus(201).end();}};RESTful Web APIDemoscriptCustom API

Design RulesDo use standard response codes as they were intended to200 for success201 if somethings has been created (specify URI of new resource in Location header)202 if controller started an async operation204 if not response was sent back intentionally (PUT, POST, DELETE)401 if something is wrong with authorization404 if no resource is present at given URI406/415 if requested/given Content-Type is not supported500 represents a server error (not the client’s fault)Consider returning additional error information in bodyUse response code 4xx and error information in response bodyDon’t expose security-critical data in error messages (especially for server errors)Use properly protected logs instead

API DesignLocation header with POSTAdditional error data incase of 4xx errorDemo

RESTful Web APIDemoscriptLocation header

RESTful Web APIDemoscriptAdditional error data

Design RulesDon’t use GET query for controller actions that writeUse proper HTTP verbs and parameters in the request body insteadDo use query for ad hoc filtering, sorting, paging, etc.Examples:https://api.myservice.com/customers? filter name eq ‘ALFKI’https://api.myservice.com/customers? top 10https://api.myservice.com/customers? orderby ?status soldSee also OData (more details later)Consider allowing correlation identifier in custom headerStored in server-side logsCan be used to correlate client- and server-side activities

Design RulesConsider support for batching of operationsPerformance considerations (latency reduction)Execute in server-side transactionsExample: Entity Group Transactions in Azure Table StorageConsider using Multipart MIME messagesExample: OData Batch RequestsConsider allowing the client to specify a server timeoutDo define a maximum server timeout to protect from over-usage of server resourcesConsider progress reporting for long running requestsExamples: Polling API, Message bus, SignalR

Design RulesConsider using Etag and If-None-Match to save bandwidthConsider using If-Match or If-Unmodified-Since for optimisticconcurrencyConsider allowing to suppress response echo on POSTTypically, POST returns created documentConsider a header with which the client can suppress this echo to save bandwith

API DesignLocation header with POSTAdditional error data incase of 4xx errorBuilding Web API withNode.jsDemoPrefer header in AzureTable Storage

RESTful Web APIDemoscriptETag and If-None-Match

RESTful Web APIDemoscriptIf-Match and optimisticconcurrency

Design RulesDo support JSON for resource representationapplication/jsonConsider other resource representation if neededE.g. application/xmlConsider adding linksProgrammatically process connections between resourcesConsider publishing schema informationFor details see OData and Swagger

API DesignLinks for entities in ODataXODataDemo

Design RulesConsider configuring CORS to enable broad web API usageDon’t solely rely on CORS for protecting your resourcesAvoid JSONP (JSON with padding)Work around same origin policy by injecting script tags at runtimeDo use OAuth2 and OpenID Connect to protect resourcesSee also Protecting Resource section later for more details

Design RulesDo limit server resource usage in multi-tenant systemsExamples:Query timeout and pagination in Azure Table StorageAPI rate limits in Azure API Management

Design RulesDo plan for versioning your web APIConsider using a custom header for API version to enable complex versioning scenariosExamplesx-ms-version in Azure Table StorageOData-MaxVersion and OData-Version headers in OdataConsider using version-specific URIs for simple versioning scenarios and major versions

Protecting ResourcesCORS – Cross-Origin Resource Sharing

What is CORS?XMLHttpReqest limits cross-domain web API callsSame origin policy: Script can only make HTTP requests to the domain it came fromCORS is a W3C spec to allow cross-domain callsSee http://enable-cors.org/client.html for browser supportServer specifies allowed calling domains in special response headersSee Mozilla Docs for technical details about TTP/Access control CORS

How CORS worksSimple requestsGET, HEAD or POSTIf POST, only content types ata, or text/plainNo custom headers in the requestBrowser sends Origin headerServer returns error if Origin in not allowed to do API callsAccess-Control headersAllow-Origin: * or OriginAllow-Credentials: Cookies included?Expose-Headers: Non-simple headers available to the client

How CORS worksNon-simple requestsPreflight requestClient asks for permissionsServer must support OPTIONSPerformance implicationsServer returns no CORS headers if not allowedActual request follows successful preflight request

CORSAdding CORS support toASP.NET Web APIDemo

Add NuGet package Microsoft.AspNet.WebApi.Corspublic static void Register(HttpConfiguration config){// New codeconfig.EnableCors();}--- or --[EnableCors(origins: "http://example.com",headers: "*", methods: "*")]public class TestController : ApiController{// Controller methods not shown.}RESTful Web APIDemoscript

Protecting ResourcesAuth with OAuth2 and OpenID Connect

Local AuthEnterpriseAuth inside of the enterpriseSingle, integrated domainWorkstationsServersDomainDevicesAll devices belong to theenterpriseEverything is WindowsProblemsExternal devicesExternal servicesNon-Windows environments

OAuth2Successor of OAuth1 and OAuth WRAPStandard for delegating authorization for accessingresources via HTTP(S)Not a standard for authenticationNot a standard for authorizationVery common in the internet todayMany different flavors as the standard leaves many decisions up to the developerExample: https://oauth.io/

Important TermsOAuth ProviderAka OAuth Server, Authorization ServerExamples: AD FS, Google, Twitter, Microsoft AADResource ProviderAka Resource ServerIn our case: A REST Web APIResource OwnerIn our case: The end user, the organizationClientApplication accessing a protected resourceIn our case: Native app, server-based web app, SPA, mobile app

OAuth EndpointsAuthorization Endpoint (aka OAuth-A)Authenticates the resource owner (e.g. user/password)Asks for consentSends confirmation (access code) to redirect endpointRedirect EndpointOffered by the clientCalled via redirecting the user-agent (HTTP redirect 302)Receives code (there are other options, too) and fetches token from token endpointToken Endpoint (aka OAuth-T)Creates tokens for access codes, refresh tokens, etc.Can validate the client using a client secret

OAuth TokensAuthorization CodeAccess TokenRefresh Token

OAuth FlowsAuthorization Code FlowAka 3-legged OAuthClient must be capable of storing secretsImplicit FlowLess secureNo refresh tokensFor clients that cannot store secrets (e.g. SPA written in JavaScript)Resource Owner Password FlowFor trusted clientsClient Credential FlowAka 2-legged OAuthClient is also the resource owner

Authorization Code FlowGetting the auth codeSource: Biehl, Matthias (2014-11-14). OAuth 2.0: Getting Startedin API Security (API-University Series Book 1)

Authorization Code FlowGetting the tokenSource: Biehl, Matthias (2014-11-14). OAuth 2.0: Getting Startedin API Security (API-University Series Book 1)

Authorization Code FlowAccessing the resourceSource: Biehl, Matthias (2014-11-14). OAuth 2.0: Getting Startedin API Security (API-University Series Book 1)

Authorization Code FlowRefreshing the tokenSource: Biehl, Matthias (2014-11-14). OAuth 2.0: Getting Startedin API Security (API-University Series Book 1)

Problems with OAuth2Many different implementationsNot compatibleLimited scopeNo specified token formats, crypto algorithms, etc.No standard for authN, session management, etc.No specification for token validationOpen ID Connect fills many of the gapsStandardized way to get the resource owner’s profile dataIntroduces an ID-TokenStandardized token format and crypto: JWT (JSON Web Token)

OIC ProtocolOpenID Connect extendsOAuth2Although rather new, OIC isalready very popularLibraries and urce: http://openid.net/connect/

Microsoft AzureMicrosoft /Europe/2014/CDP-B210

Standards based integrationsCustom LOB applications that integrate with Azure Active DirectorySign in to Active Directory-integratedapplications with cloud identitiesActive Directory-integrated applicationscan access Office 365 and other web APIsApplications can extend AzureActive Directory schemaCross-platform supportiOS, Android, and WindowsOpen StandardsSAML, OAuth 2.0, OpenID Connect, ODataSource: /CDP-B210

Web API MetadataThe role of metadata using the examples of http://swagger.io/ and OData

Why Metadata?Humans and computers discover and understand servicesLess need to read documentation or source codeEnables tools for the API creatorWrite less documentation manuallyMake consuming the API easier raises adoptionEnables tools for the API consumerBuild generic service consumerExamples: BI tools like PowerBI, workflow engines like Azure Logic AppsAuto-generate client code/libraries

Swaggerhttp://swagger.ioTools for API creatorsSwagger Editor (http://editor.swagger.io/) for top-down approachAuto-generate Swagger definition from server-side implementationExample: s for API consumersSwagger UI (http://petstore.swagger.io/)Code generators )

SwaggerSwagger editorSwagger code generator(AngularJS)Demo

OData – Much More than Metadatahttp://www.odata.orgCommon Schema Definition Language (CSDL)OASIS /odata/v4.0/odata-v4.0-part3-csdl.htmlLibraries for API creators and consumershttp://www.odata.org/libraries/Widely used at Microsoft and SAPExamples: Microsoft Azure, PowerBI, Visual Studio

OData – Much More than MetadataCRUD operationsRESTful web APIStandardized query language using URIshttps://api.myserver.com/odata/Customers? filter CustomerID eq 15& top 10& select tandardized document representationXML (Atom), rmat/v4.0/odata-json-format-v4.0.html

ODataImplementing an ODataservice in .NETOData consumptionXODataPower BIDemo

Software Architecture Summit 2015Rainer Stropeksoftware architects gmbhQ&AMail rainer@timecockpit.comWeb http://www.timecockpit.comTwitter @rstropekThank your for coming!Saves the day.

is the leading time tracking solution for knowledge workers.Graphical time tracking calendar, automatic tracking of your work usingsignal trackers, high level of extensibility and customizability, full support towork offline, and SaaS deployment model make it the optimal choiceespecially in the IT consulting business.Tryfor free and without any risk. You can get your trial accountat http://www.timecockpit.com. After the trial period you can usefor only 0,25 per user and day without a minimal subscription time andwithout a minimal number of users.

ist die führende Projektzeiterfassung für Knowledge Worker.Grafischer Zeitbuchungskalender, automatische Tätigkeitsaufzeichnung überSignal Tracker, umfassende Erweiterbarkeit und Anpassbarkeit, volleOfflinefähigkeit und einfachste Verwendung durch SaaS machen es zurOptimalen Lösung auch speziell im IT-Umfeld.Probieren Siekostenlos und ohne Risiko einfach aus. EinenTestzugang erhalten Sie unter http://www.timecockpit.com. Danach nutzenSieum nur 0,25 pro Benutzer und Tag ohne Mindestdauerund ohne Mindestbenutzeranzahl.

Web API Design Web Mail Twitter. Agenda RESTful Web APIs have become an integral part of modern software packages. They are important for integration scenarios in enterprises and in the cloud. This workshop is dedicated to designing RESTful Web APIs. Rainer Stropek, himself founder a