From 700d5c8fb06de86c587cf6089f95d383404f45ce Mon Sep 17 00:00:00 2001 From: erinspace Date: Wed, 22 Feb 2017 13:57:21 -0500 Subject: [PATCH 1/3] Revert "Temporarily disable try-it-out for non-GET endpoints. (#29)" This reverts commit 8950abbe4533838c29fb7cadcdcfde99bcdca170. --- src/main/javascript/view/OperationView.js | 1 - src/main/template/operation.handlebars | 75 ++++++++++++----------- 2 files changed, 39 insertions(+), 37 deletions(-) diff --git a/src/main/javascript/view/OperationView.js b/src/main/javascript/view/OperationView.js index 2c5c633ff36..273e6348891 100644 --- a/src/main/javascript/view/OperationView.js +++ b/src/main/javascript/view/OperationView.js @@ -26,7 +26,6 @@ SwaggerUi.Views.OperationView = Backbone.View.extend({ this.nickname = this.model.nickname; this.model.encodedParentId = encodeURIComponent(this.parentId); this.model.endpoint = api_topics.indexOf(this.model.summary) == -1 ? true : false; - this.model.read = this.model.method == 'get'; this.schemaName = this.model.operation['x-response-schema']; return this; }, diff --git a/src/main/template/operation.handlebars b/src/main/template/operation.handlebars index 618d3661422..8e38467ab0d 100644 --- a/src/main/template/operation.handlebars +++ b/src/main/template/operation.handlebars @@ -40,48 +40,51 @@
{{#if endpoint}} - {{#if read}} - {{#if parameters}} -

- Parameters -

-
- {{/if}} -
-
- - Hide Response - - - - {{#oauth}} -
- {{/oauth}} - - {{#each oauth}} - - {{/each}} - - {{#oauth}} - + {{#if parameters}} +

+ Parameters +

+
+ {{/if}} + +{{!--

+ Test this endpoint +

+ --}} +
+
+ + Hide Response + + + + {{#oauth}} +
+ {{/oauth}} + + {{#each oauth}} + - {{/oauth}} + {{/each}} + {{#oauth}} +
- - {{#if type}} -
- {{/if}} + {{/oauth}}
- {{/if}} + + {{#if type}} +
+ {{/if}} + +
{{!-- {{#if responseMessages}}
From 4cedbd2472b40e3e9189b0feb31f6e24dd51d9e1 Mon Sep 17 00:00:00 2001 From: erinspace Date: Wed, 22 Feb 2017 13:58:18 -0500 Subject: [PATCH 2/3] Merge things --- src/main/javascript/view/MainView.js | 55 ++++++++++++++-------------- 1 file changed, 28 insertions(+), 27 deletions(-) diff --git a/src/main/javascript/view/MainView.js b/src/main/javascript/view/MainView.js index e484a940469..13d371bbc51 100644 --- a/src/main/javascript/view/MainView.js +++ b/src/main/javascript/view/MainView.js @@ -137,6 +137,7 @@ SwaggerUi.Views.MainView = Backbone.View.extend({ this.addResource(resource, this.model.auths); this.addSidebarHeader(resource, i); + this.addSidebarToken(resource, i); } $('.propWrap').hover(function onHover() { @@ -173,23 +174,23 @@ SwaggerUi.Views.MainView = Backbone.View.extend({ $('#resources').append(resourceView.render().el); }, - // addSidebarToken: function (resource, i) { - // resource.id = resource.id.replace(/\s/g, '_'); - // var sidebarView = new SwaggerUi.Views.SidebarHeaderView({ - // model: resource, - // tagName: 'div', - // className: function () { - // return i == 0 ? 'active' : '' - // }, - // attributes: { - // "data-resource": 'resource_' + resource.name, - // "label": resource.name - // }, - // router: this.router, - // swaggerOptions: this.options.swaggerOptions - // }); - // $('#token-generator', $(this.el)).append(sidebarView.render().el); - // }, + addSidebarToken: function (resource, i) { + resource.id = resource.id.replace(/\s/g, '_'); + var sidebarView = new SwaggerUi.Views.SidebarHeaderView({ + model: resource, + tagName: 'div', + className: function () { + return i == 0 ? 'active' : '' + }, + attributes: { + "data-resource": 'resource_' + resource.name, + "label": resource.name + }, + router: this.router, + swaggerOptions: this.options.swaggerOptions + }); + $('#token-generator', $(this.el)).append(sidebarView.render().el); + }, addSidebarHeader: function (resource, i) { @@ -240,7 +241,7 @@ SwaggerUi.Views.MainView = Backbone.View.extend({ } }); - } + }, // toggleToken: function (e) { // var t = $(".token-generator"), @@ -269,13 +270,13 @@ SwaggerUi.Views.MainView = Backbone.View.extend({ // t.parents(".sticky-nav").trigger("mobile_nav:update") // }, - // showCustom: function(e){ - // if (e) { - // e.preventDefault(); - // } - // this.trigger('update-swagger-ui', { - // url: $('#input_baseUrl').val(), - // apiKey: $('#input_apiKey').val() - // }); - // } + showCustom: function(e){ + if (e) { + e.preventDefault(); + } + this.trigger('update-swagger-ui', { + url: $('#input_baseUrl').val(), + apiKey: $('#input_apiKey').val() + }); + } }); From 56adf64add0e385059da8966f5a64159aeed924c Mon Sep 17 00:00:00 2001 From: erinspace Date: Thu, 23 Feb 2017 17:26:24 -0500 Subject: [PATCH 3/3] Add API token header auth for interactive use of the API! - Update swagger.yaml to include API header auth - Also include a link to where to set your token - Template updates to show auth info where appropriate - Clear and reset the token from the sidebar - CSS and style updates - helper function to compare the type of request and if you have a key or not future improvements: - simply disable the "TRY" button with no key, don't hide the form entirely --- src/main/html/css/api-explorer.css | 42 ++++++++++ src/main/html/index.html | 18 ----- src/main/javascript/helpers/handlebars.js | 10 ++- src/main/javascript/view/ApiKeyButton.js | 38 +++++++--- src/main/javascript/view/MainView.js | 76 +++++++++---------- .../template/apikey_button_view.handlebars | 8 +- src/main/template/main.handlebars | 7 ++ src/main/template/operation.handlebars | 16 +++- swagger-spec/swagger.yaml | 10 ++- 9 files changed, 150 insertions(+), 75 deletions(-) diff --git a/src/main/html/css/api-explorer.css b/src/main/html/css/api-explorer.css index 4368e9909c4..5d93a2ae7f6 100644 --- a/src/main/html/css/api-explorer.css +++ b/src/main/html/css/api-explorer.css @@ -2474,3 +2474,45 @@ body { padding-top: 10px; color: lightblue; } + +.auth-container { + margin: 20px 20px 20px; +} + +.auth_input { + margin-top: 6px; + padding-top: 6px; + padding-bottom: 7px; + padding-left: 12px; + font-family: inherit; + +} + +.token-indicator { + font-size: smaller; + margin-top: 5px; + font-style: italic; + font-family: inherit; +} + +.osf-token-info { + font-size: smaller; + margin-top: 5px; + font-style: italic; + font-family: inherit; +} + +.try-hide { + font-family: inherit; + font-size: inherit; + font-color: inherit; +} + +.put-post-patch-info { + background-color: #d9edf7; +} + +#clear-token-link { + padding-left: 57px; + cursor: pointer; +} diff --git a/src/main/html/index.html b/src/main/html/index.html index a0f9ebcf590..07574f28979 100644 --- a/src/main/html/index.html +++ b/src/main/html/index.html @@ -108,7 +108,6 @@ }); } - // addApiKeyAuthorization(); }, onFailure: function (data) { log("Unable to Load SwaggerUI"); @@ -116,23 +115,6 @@ docExpansion: "none", sorter: "alpha" }); - - // function addApiKeyAuthorization() { - // var key = encodeURIComponent($('#input_apiKey')[0].value); - // if (key && key.trim() != "") { - // var apiKeyAuth = new SwaggerClient.ApiKeyAuthorization("Authorization", "Bearer " + key, "header"); - // window.swaggerUi.api.clientAuthorizations.add("key", apiKeyAuth); - // log("added key " + key); - // } - // } - - // $('#input_apiKey').change(addApiKeyAuthorization); - // if you have an apiKey you would like to pre-populate on the page for demonstration purposes... - /* - var apiKey = "myApiKeyXXXX123456789"; - $('#input_apiKey').val(apiKey); - */ - window.swaggerUi.load(); function log() { diff --git a/src/main/javascript/helpers/handlebars.js b/src/main/javascript/helpers/handlebars.js index 58a43d70530..7d21c8957d1 100644 --- a/src/main/javascript/helpers/handlebars.js +++ b/src/main/javascript/helpers/handlebars.js @@ -4,4 +4,12 @@ Handlebars.registerHelper('sanitize', function(html) { // Strip the script tags from the html, and return it as a Handlebars.SafeString html = html.replace(/)<[^<]*)*<\/script>/gi, ''); return new Handlebars.SafeString(html); -}); \ No newline at end of file +}); + +Handlebars.registerHelper('notequal', function(value1, value2, options) { + if (value1 == value2) { + return options.inverse(this); + } else { + return options.fn(this); + } +}); diff --git a/src/main/javascript/view/ApiKeyButton.js b/src/main/javascript/view/ApiKeyButton.js index 941766b1f8b..ebebf5f6c98 100644 --- a/src/main/javascript/view/ApiKeyButton.js +++ b/src/main/javascript/view/ApiKeyButton.js @@ -4,7 +4,8 @@ SwaggerUi.Views.ApiKeyButton = Backbone.View.extend({ // TODO: append this to gl events:{ 'click #apikey_button' : 'toggleApiKeyContainer', - 'click #apply_api_key' : 'applyApiKey' + 'click #apply_api_key' : 'applyApiKey', + 'click #clear-token-link': 'removeApiKey' }, initialize: function(opts){ @@ -15,19 +16,21 @@ SwaggerUi.Views.ApiKeyButton = Backbone.View.extend({ // TODO: append this to gl render: function(){ var template = this.template(); $(this.el).html(template(this.model)); - return this; }, - applyApiKey: function(){ - var keyAuth = new SwaggerClient.ApiKeyAuthorization( - this.model.name, - $('#input_apiKey_entry').val(), - this.model.in - ); - this.router.api.clientAuthorizations.add(this.model.name, keyAuth); - this.router.load(); + var key = encodeURIComponent($('#input_apiKey_entry')[0].value); + if (key && key.trim() != "") { + var apiKeyAuth = new SwaggerClient.ApiKeyAuthorization("Authorization", "Bearer " + key, "header"); + this.router.api.clientAuthorizations.add("key", apiKeyAuth); + $('.token-indicator').removeClass("hidden"); + $('.osf-token-info').addClass("hidden"); + $('.put-post-patch-try').removeClass("hidden"); + $('.put-post-patch-info').addClass("hidden"); + } else { + this.removeApiKey(); + } $('#apikey_container').show(); }, @@ -35,10 +38,14 @@ SwaggerUi.Views.ApiKeyButton = Backbone.View.extend({ // TODO: append this to gl if ($('#apikey_container').length) { var elem = $('#apikey_container').first(); + var button = $('#apikey_menu_icon'); if (elem.is(':visible')){ elem.hide(); + button.removeClass("glyphicon-menu-down").addClass("glyphicon glyphicon-menu-right"); + } else { + button.removeClass("glyphicon-menu-right").addClass("glyphicon-menu-down"); // hide others $('.auth_container').hide(); @@ -49,6 +56,15 @@ SwaggerUi.Views.ApiKeyButton = Backbone.View.extend({ // TODO: append this to gl template: function(){ return Handlebars.templates.apikey_button_view; + }, + + removeApiKey: function() { + this.router.api.clientAuthorizations.remove("key"); + $('#input_apiKey_entry')[0].value = ''; + $('.token-indicator').addClass("hidden"); + $('.osf-token-info').removeClass("hidden"); + $('.put-post-patch-try').addClass("hidden"); + $('.put-post-patch-info').removeClass("hidden"); } -}); \ No newline at end of file +}); diff --git a/src/main/javascript/view/MainView.js b/src/main/javascript/view/MainView.js index 13d371bbc51..4f0d507330d 100644 --- a/src/main/javascript/view/MainView.js +++ b/src/main/javascript/view/MainView.js @@ -100,23 +100,6 @@ SwaggerUi.Views.MainView = Backbone.View.extend({ }, render: function () { - if (this.model.securityDefinitions) { - for (var name in this.model.securityDefinitions) { - var auth = this.model.securityDefinitions[name]; - var button; - - if (auth.type === 'apiKey' && $('#apikey_button').length === 0) { - button = new SwaggerUi.Views.ApiKeyButton({model: auth, router: this.router}).render().el; - $('.auth_main_container').append(button); - } - - if (auth.type === 'basicAuth' && $('#basic_auth_button').length === 0) { - button = new SwaggerUi.Views.BasicAuthButton({model: auth, router: this.router}).render().el; - $('.auth_main_container').append(button); - } - } - } - // Render the outer container for resources $(this.el).html(Handlebars.templates.main(this.model)); @@ -152,6 +135,23 @@ SwaggerUi.Views.MainView = Backbone.View.extend({ $(window).scrollTop(0) } + if (this.model.securityDefinitions) { + for (var name in this.model.securityDefinitions) { + var auth = this.model.securityDefinitions[name]; + var button; + + if (auth.type === 'apiKey' && $('#apikey_button').length === 0) { + button = new SwaggerUi.Views.ApiKeyButton({model: auth, router: this.router}).render().el; + $('.auth_main_container').append(button); + } + + if (auth.type === 'basicAuth' && $('#basic_auth_button').length === 0) { + button = new SwaggerUi.Views.BasicAuthButton({model: auth, router: this.router}).render().el; + $('.auth_main_container').append(button); + } + } + } + return this; }, @@ -243,32 +243,32 @@ SwaggerUi.Views.MainView = Backbone.View.extend({ }, - // toggleToken: function (e) { - // var t = $(".token-generator"), - // tg = $("[data-tg-switch]"); + toggleToken: function (e) { + var t = $(".token-generator"), + tg = $("[data-tg-switch]"); - // t.toggleClass("hide"); - // t.hasClass("hide") ? tg.removeClass("active") : tg.addClass("active"); - // t.parents(".sticky-nav").trigger("mobile_nav:update") - // }, + t.toggleClass("hide"); + t.hasClass("hide") ? tg.removeClass("active") : tg.addClass("active"); + t.parents(".sticky-nav").trigger("mobile_nav:update") + }, - // closeToken: function (e) { - // var t = $(".token-generator"), - // tg = $("[data-tg-switch]"); + closeToken: function (e) { + var t = $(".token-generator"), + tg = $("[data-tg-switch]"); - // t.addClass("hide"); - // tg.removeClass("active"); - // t.parents(".sticky-nav").trigger("mobile_nav:update") - // }, + t.addClass("hide"); + tg.removeClass("active"); + t.parents(".sticky-nav").trigger("mobile_nav:update") + }, - // openToken: function (e) { - // var t = $(".token-generator"), - // tg = $("[data-tg-switch]"); + openToken: function (e) { + var t = $(".token-generator"), + tg = $("[data-tg-switch]"); - // t.removeClass("hide"); - // tg.removeClass("active"); - // t.parents(".sticky-nav").trigger("mobile_nav:update") - // }, + t.removeClass("hide"); + tg.removeClass("active"); + t.parents(".sticky-nav").trigger("mobile_nav:update") + }, showCustom: function(e){ if (e) { diff --git a/src/main/template/apikey_button_view.handlebars b/src/main/template/apikey_button_view.handlebars index 83d52ff248b..7c8c488e858 100644 --- a/src/main/template/apikey_button_view.handlebars +++ b/src/main/template/apikey_button_view.handlebars @@ -1,11 +1,11 @@
- + API Authorization
{{keyName}}
- - + +
+
- diff --git a/src/main/template/main.handlebars b/src/main/template/main.handlebars index d9539fc918e..6488aeddcb6 100644 --- a/src/main/template/main.handlebars +++ b/src/main/template/main.handlebars @@ -5,6 +5,13 @@ OSF API
+
+
+
+ +
API Reference:
diff --git a/src/main/template/operation.handlebars b/src/main/template/operation.handlebars index 8e38467ab0d..2040e9439cb 100644 --- a/src/main/template/operation.handlebars +++ b/src/main/template/operation.handlebars @@ -37,6 +37,13 @@
{{{description}}}
{{/if}} + {{#notequal this.method 'get'}} +

To enable the "try it out" feature for patch, post, or delete requests, + enter an OSF API Token at the top of the sidebar.

+
+
diff --git a/swagger-spec/swagger.yaml b/swagger-spec/swagger.yaml index 2531e69de45..f3e899c547a 100644 --- a/swagger-spec/swagger.yaml +++ b/swagger-spec/swagger.yaml @@ -10,12 +10,20 @@ info: name: OSF email: support@osf.io url: 'https://osf.io/support' + x-token-settings: 'https://test.osf.io/settings/tokens/' license: name: Apache 2.0 url: 'http://www.apache.org/licenses/LICENSE-2.0.html' host: 'test-api.osf.io' schemes: - - https + - http +securityDefinitions: + api_key: + type: apiKey + in: header + name: api_key + basic: + type: basic basePath: /v2 paths: