diff --git a/core/client/app/controllers/feature.js b/core/client/app/controllers/feature.js
index b584296653..5aa36375eb 100644
--- a/core/client/app/controllers/feature.js
+++ b/core/client/app/controllers/feature.js
@@ -25,5 +25,9 @@ export default Ember.Controller.extend(Ember.PromiseProxyMixin, {
}
return value;
+ }),
+
+ publicAPI: Ember.computed('config.publicAPI', 'labs.publicAPI', function () {
+ return this.get('config.publicAPI') || this.get('labs.publicAPI');
})
});
diff --git a/core/client/app/controllers/settings/labs.js b/core/client/app/controllers/settings/labs.js
index 42b29a2238..2a70142721 100644
--- a/core/client/app/controllers/settings/labs.js
+++ b/core/client/app/controllers/settings/labs.js
@@ -9,6 +9,7 @@ export default Ember.Controller.extend({
ghostPaths: Ember.inject.service('ghost-paths'),
notifications: Ember.inject.service(),
session: Ember.inject.service(),
+ feature: Ember.inject.controller(),
labsJSON: Ember.computed('model.labs', function () {
return JSON.parse(this.get('model.labs') || {});
@@ -29,6 +30,16 @@ export default Ember.Controller.extend({
});
},
+ usePublicAPI: Ember.computed('feature.publicAPI', {
+ get: function () {
+ return this.get('feature.publicAPI');
+ },
+ set: function (key, value) {
+ this.saveLabs('publicAPI', value);
+ return value;
+ }
+ }),
+
actions: {
onUpload: function (file) {
var self = this,
diff --git a/core/client/app/templates/settings/labs.hbs b/core/client/app/templates/settings/labs.hbs
index 8494c7c8b7..96baf4df1e 100644
--- a/core/client/app/templates/settings/labs.hbs
+++ b/core/client/app/templates/settings/labs.hbs
@@ -42,5 +42,19 @@
+
+
diff --git a/core/server/api/configuration.js b/core/server/api/configuration.js
index 3b1067db6f..9bcf48a612 100644
--- a/core/server/api/configuration.js
+++ b/core/server/api/configuration.js
@@ -10,6 +10,7 @@ var _ = require('lodash'),
function getValidKeys() {
var validKeys = {
fileStorage: config.fileStorage === false ? false : true,
+ publicAPI: config.publicAPI === true ? true : false,
apps: config.apps === true ? true : false,
version: config.ghostVersion,
environment: process.env.NODE_ENV,
diff --git a/core/server/middleware/auth.js b/core/server/middleware/auth.js
index 59100b34e3..79ff74826e 100644
--- a/core/server/middleware/auth.js
+++ b/core/server/middleware/auth.js
@@ -3,6 +3,7 @@ var _ = require('lodash'),
url = require('url'),
errors = require('../errors'),
config = require('../config'),
+ api = require('../api'),
oauthServer,
auth;
@@ -130,6 +131,30 @@ auth = {
}
},
+ // ### Require user depending on public API being activated.
+ requiresAuthorizedUserPublicAPI: function requiresAuthorizedUserPublicAPI(req, res, next) {
+ return api.settings.read({key: 'labs', context: {internal: true}}).then(function (response) {
+ var labs,
+ labsValue;
+
+ labs = _.find(response.settings, function (setting) {
+ return setting.key === 'labs';
+ });
+
+ labsValue = JSON.parse(labs.value);
+
+ if (labsValue.publicAPI && labsValue.publicAPI === true) {
+ return next();
+ } else {
+ if (req.user) {
+ return next();
+ } else {
+ return errors.handleAPIError(new errors.NoPermissionError('Please Sign In'), req, res, next);
+ }
+ }
+ });
+ },
+
// ### Generate access token Middleware
// register the oauth2orize middleware for password and refresh token grants
generateAccessToken: function generateAccessToken(req, res, next) {
diff --git a/core/server/middleware/index.js b/core/server/middleware/index.js
index 41aa34c9f8..3846e2529f 100644
--- a/core/server/middleware/index.js
+++ b/core/server/middleware/index.js
@@ -43,6 +43,7 @@ middleware = {
authenticateClient: auth.authenticateClient,
authenticateUser: auth.authenticateUser,
requiresAuthorizedUser: auth.requiresAuthorizedUser,
+ requiresAuthorizedUserPublicAPI: auth.requiresAuthorizedUserPublicAPI,
generateAccessToken: auth.generateAccessToken,
errorHandler: errors.handleAPIError
}
diff --git a/core/server/routes/api.js b/core/server/routes/api.js
index b8b0baa993..ac2b875619 100644
--- a/core/server/routes/api.js
+++ b/core/server/routes/api.js
@@ -8,7 +8,8 @@ apiRoutes = function apiRoutes(middleware) {
// Authentication for public endpoints
authenticatePublic = [
middleware.api.authenticateClient,
- middleware.api.authenticateUser
+ middleware.api.authenticateUser,
+ middleware.api.requiresAuthorizedUserPublicAPI
],
// Require user for private endpoints
authenticatePrivate = [
diff --git a/core/test/functional/routes/api/public_api_spec.js b/core/test/functional/routes/api/public_api_spec.js
index 6a388a5b1d..ff541fb68d 100644
--- a/core/test/functional/routes/api/public_api_spec.js
+++ b/core/test/functional/routes/api/public_api_spec.js
@@ -10,6 +10,12 @@ var testUtils = require('../../../utils'),
request;
describe('Public API', function () {
+ var publicAPIaccessSetting = {
+ settings: [
+ {key: 'labs', value: {publicAPI: true}}
+ ]
+ };
+
before(function (done) {
// starting ghost automatically populates the db
// TODO: prevent db init, and manage bringing up the DB with fixtures ourselves
@@ -17,8 +23,20 @@ describe('Public API', function () {
request = supertest.agent(ghostServer.rootApp);
}).then(function () {
return testUtils.doAuth(request, 'posts', 'tags');
- }).then(function () {
- done();
+ }).then(function (token) {
+ // enable public API
+ return request.put(testUtils.API.getApiQuery('settings/'))
+ .set('Authorization', 'Bearer ' + token)
+ .send(publicAPIaccessSetting)
+ .expect('Content-Type', /json/)
+ .expect('Cache-Control', testUtils.cacheRules.private)
+ .expect(200)
+ .end(function (err) {
+ if (err) {
+ return done(err);
+ }
+ done();
+ });
}).catch(done);
});