mirror of
https://github.com/NodeBB/NodeBB.git
synced 2025-11-02 12:05:57 +01:00
@@ -69,19 +69,16 @@ uploadsController.get = function (req, res, next) {
|
|||||||
setImmediate(next, null, files);
|
setImmediate(next, null, files);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
], function (err, files) {
|
function (files) {
|
||||||
if (err) {
|
res.render('admin/manage/uploads', {
|
||||||
return next(err);
|
currentFolder: currentFolder.replace(nconf.get('upload_path'), ''),
|
||||||
}
|
showPids: files.length && files[0].hasOwnProperty('inPids'),
|
||||||
|
files: files,
|
||||||
res.render('admin/manage/uploads', {
|
breadcrumbs: buildBreadcrumbs(currentFolder),
|
||||||
currentFolder: currentFolder.replace(nconf.get('upload_path'), ''),
|
pagination: pagination.create(page, Math.ceil(itemCount / itemsPerPage), req.query),
|
||||||
showPids: files.length && files[0].hasOwnProperty('inPids'),
|
});
|
||||||
files: files,
|
},
|
||||||
breadcrumbs: buildBreadcrumbs(currentFolder),
|
], next);
|
||||||
pagination: pagination.create(page, Math.ceil(itemCount / itemsPerPage), req.query),
|
|
||||||
});
|
|
||||||
});
|
|
||||||
};
|
};
|
||||||
|
|
||||||
function buildBreadcrumbs(currentFolder) {
|
function buildBreadcrumbs(currentFolder) {
|
||||||
|
|||||||
@@ -111,8 +111,8 @@ userController.exportPosts = function (req, res, next) {
|
|||||||
async.waterfall([
|
async.waterfall([
|
||||||
function (next) {
|
function (next) {
|
||||||
var payload = [];
|
var payload = [];
|
||||||
batch.processSortedSet('uid:' + req.params.uid + ':posts', function (pids, next) {
|
batch.processSortedSet('uid:' + res.locals.uid + ':posts', function (pids, next) {
|
||||||
async.map(pids, posts.getPostData, function (err, posts) {
|
posts.getPostsData(pids, function (err, posts) {
|
||||||
if (err) {
|
if (err) {
|
||||||
return next(err);
|
return next(err);
|
||||||
}
|
}
|
||||||
@@ -136,22 +136,19 @@ userController.exportPosts = function (req, res, next) {
|
|||||||
emptyFieldValue: '',
|
emptyFieldValue: '',
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
], function (err, csv) {
|
function (csv) {
|
||||||
if (err) {
|
res.set('Content-Type', 'text/csv').set('Content-Disposition', 'attachment; filename="' + req.params.uid + '_posts.csv"').send(csv);
|
||||||
return next(err);
|
},
|
||||||
}
|
], next);
|
||||||
|
|
||||||
res.set('Content-Type', 'text/csv').set('Content-Disposition', 'attachment; filename="' + req.params.uid + '_posts.csv"').send(csv);
|
|
||||||
});
|
|
||||||
};
|
};
|
||||||
|
|
||||||
userController.exportUploads = function (req, res, next) {
|
userController.exportUploads = function (req, res, next) {
|
||||||
const archivePath = path.join(__dirname, '../../build/export', req.params.uid + '_uploads.zip');
|
const targetUid = res.locals.uid;
|
||||||
|
const archivePath = path.join(__dirname, '../../build/export', targetUid + '_uploads.zip');
|
||||||
const archive = archiver('zip', {
|
const archive = archiver('zip', {
|
||||||
zlib: { level: 9 }, // Sets the compression level.
|
zlib: { level: 9 }, // Sets the compression level.
|
||||||
});
|
});
|
||||||
const maxAge = 1000 * 60 * 60 * 24; // 1 day
|
const maxAge = 1000 * 60 * 60 * 24; // 1 day
|
||||||
|
|
||||||
const rootDirectory = path.join(__dirname, '../../public/uploads/');
|
const rootDirectory = path.join(__dirname, '../../public/uploads/');
|
||||||
const trimPath = function (path) {
|
const trimPath = function (path) {
|
||||||
return path.replace(rootDirectory, '');
|
return path.replace(rootDirectory, '');
|
||||||
@@ -161,15 +158,15 @@ userController.exportUploads = function (req, res, next) {
|
|||||||
events.log({
|
events.log({
|
||||||
type: 'export:uploads',
|
type: 'export:uploads',
|
||||||
uid: req.uid,
|
uid: req.uid,
|
||||||
targetUid: req.params.uid,
|
targetUid: targetUid,
|
||||||
ip: req.ip,
|
ip: req.ip,
|
||||||
fresh: isFresh,
|
fresh: isFresh,
|
||||||
});
|
});
|
||||||
|
|
||||||
res.sendFile(req.params.uid + '_uploads.zip', {
|
res.sendFile(targetUid + '_uploads.zip', {
|
||||||
root: path.join(__dirname, '../../build/export'),
|
root: path.join(__dirname, '../../build/export'),
|
||||||
headers: {
|
headers: {
|
||||||
'Content-Disposition': 'attachment; filename=' + req.params.uid + '_uploads.zip',
|
'Content-Disposition': 'attachment; filename=' + targetUid + '_uploads.zip',
|
||||||
maxAge: maxAge,
|
maxAge: maxAge,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
@@ -216,8 +213,8 @@ userController.exportUploads = function (req, res, next) {
|
|||||||
});
|
});
|
||||||
|
|
||||||
archive.pipe(output);
|
archive.pipe(output);
|
||||||
winston.info('[user/export/uploads] Collating uploads for uid ' + req.params.uid);
|
winston.info('[user/export/uploads] Collating uploads for uid ' + targetUid);
|
||||||
user.collateUploads(req.params.uid, archive, function (err) {
|
user.collateUploads(targetUid, archive, function (err) {
|
||||||
if (err) {
|
if (err) {
|
||||||
return next(err);
|
return next(err);
|
||||||
}
|
}
|
||||||
@@ -227,19 +224,17 @@ userController.exportUploads = function (req, res, next) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
userController.exportProfile = function (req, res, next) {
|
userController.exportProfile = function (req, res, next) {
|
||||||
|
const targetUid = res.locals.uid;
|
||||||
async.waterfall([
|
async.waterfall([
|
||||||
async.apply(db.getObjects.bind(db), ['user:' + req.params.uid, 'user:' + req.params.uid + ':settings']),
|
async.apply(db.getObjects.bind(db), ['user:' + targetUid, 'user:' + targetUid + ':settings']),
|
||||||
function (objects, next) {
|
function (objects, next) {
|
||||||
Object.assign(objects[0], objects[1]);
|
Object.assign(objects[0], objects[1]);
|
||||||
delete objects[0].password;
|
delete objects[0].password;
|
||||||
|
|
||||||
converter.json2csv(objects[0], next);
|
converter.json2csv(objects[0], next);
|
||||||
},
|
},
|
||||||
], function (err, csv) {
|
function (csv) {
|
||||||
if (err) {
|
res.set('Content-Type', 'text/csv').set('Content-Disposition', 'attachment; filename="' + targetUid + '_profile.csv"').send(csv);
|
||||||
return next(err);
|
},
|
||||||
}
|
], next);
|
||||||
|
|
||||||
res.set('Content-Type', 'text/csv').set('Content-Disposition', 'attachment; filename="' + req.params.uid + '_profile.csv"').send(csv);
|
|
||||||
});
|
|
||||||
};
|
};
|
||||||
|
|||||||
14
src/posts.js
14
src/posts.js
@@ -109,6 +109,20 @@ Posts.getPostData = function (pid, callback) {
|
|||||||
], callback);
|
], callback);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Posts.getPostsData = function (pids, callback) {
|
||||||
|
async.waterfall([
|
||||||
|
function (next) {
|
||||||
|
db.getObjects(pids.map(pid => 'post:' + pid), next);
|
||||||
|
},
|
||||||
|
function (data, next) {
|
||||||
|
plugins.fireHook('filter:post.getPostsData', { posts: data }, next);
|
||||||
|
},
|
||||||
|
function (data, next) {
|
||||||
|
next(null, data.posts);
|
||||||
|
},
|
||||||
|
], callback);
|
||||||
|
};
|
||||||
|
|
||||||
Posts.getPostField = function (pid, field, callback) {
|
Posts.getPostField = function (pid, field, callback) {
|
||||||
async.waterfall([
|
async.waterfall([
|
||||||
function (next) {
|
function (next) {
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ module.exports = function (app, middleware, controllers) {
|
|||||||
setupPageRoute(app, '/user/:userslug', middleware, middlewares, controllers.accounts.profile.get);
|
setupPageRoute(app, '/user/:userslug', middleware, middlewares, controllers.accounts.profile.get);
|
||||||
setupPageRoute(app, '/user/:userslug/following', middleware, middlewares, controllers.accounts.follow.getFollowing);
|
setupPageRoute(app, '/user/:userslug/following', middleware, middlewares, controllers.accounts.follow.getFollowing);
|
||||||
setupPageRoute(app, '/user/:userslug/followers', middleware, middlewares, controllers.accounts.follow.getFollowers);
|
setupPageRoute(app, '/user/:userslug/followers', middleware, middlewares, controllers.accounts.follow.getFollowers);
|
||||||
setupPageRoute(app, '/user/:userslug/blocks', middleware, middlewares, controllers.accounts.blocks.getBlocks);
|
|
||||||
setupPageRoute(app, '/user/:userslug/posts', middleware, middlewares, controllers.accounts.posts.getPosts);
|
setupPageRoute(app, '/user/:userslug/posts', middleware, middlewares, controllers.accounts.posts.getPosts);
|
||||||
setupPageRoute(app, '/user/:userslug/topics', middleware, middlewares, controllers.accounts.posts.getTopics);
|
setupPageRoute(app, '/user/:userslug/topics', middleware, middlewares, controllers.accounts.posts.getTopics);
|
||||||
setupPageRoute(app, '/user/:userslug/best', middleware, middlewares, controllers.accounts.posts.getBestPosts);
|
setupPageRoute(app, '/user/:userslug/best', middleware, middlewares, controllers.accounts.posts.getBestPosts);
|
||||||
@@ -32,6 +32,7 @@ module.exports = function (app, middleware, controllers) {
|
|||||||
setupPageRoute(app, '/user/:userslug/settings', middleware, accountMiddlewares, controllers.accounts.settings.get);
|
setupPageRoute(app, '/user/:userslug/settings', middleware, accountMiddlewares, controllers.accounts.settings.get);
|
||||||
setupPageRoute(app, '/user/:userslug/uploads', middleware, accountMiddlewares, controllers.accounts.uploads.get);
|
setupPageRoute(app, '/user/:userslug/uploads', middleware, accountMiddlewares, controllers.accounts.uploads.get);
|
||||||
setupPageRoute(app, '/user/:userslug/consent', middleware, accountMiddlewares, controllers.accounts.consent.get);
|
setupPageRoute(app, '/user/:userslug/consent', middleware, accountMiddlewares, controllers.accounts.consent.get);
|
||||||
|
setupPageRoute(app, '/user/:userslug/blocks', middleware, accountMiddlewares, controllers.accounts.blocks.getBlocks);
|
||||||
|
|
||||||
app.delete('/api/user/:userslug/session/:uuid', [middleware.exposeUid, middleware.ensureSelfOrGlobalPrivilege], controllers.accounts.session.revoke);
|
app.delete('/api/user/:userslug/session/:uuid', [middleware.exposeUid, middleware.ensureSelfOrGlobalPrivilege], controllers.accounts.session.revoke);
|
||||||
|
|
||||||
|
|||||||
@@ -15,9 +15,9 @@ module.exports = function (app, middleware, controllers) {
|
|||||||
router.get('/user/username/:username', middleware.checkGlobalPrivacySettings, controllers.user.getUserByUsername);
|
router.get('/user/username/:username', middleware.checkGlobalPrivacySettings, controllers.user.getUserByUsername);
|
||||||
router.get('/user/email/:email', middleware.checkGlobalPrivacySettings, controllers.user.getUserByEmail);
|
router.get('/user/email/:email', middleware.checkGlobalPrivacySettings, controllers.user.getUserByEmail);
|
||||||
|
|
||||||
router.get('/user/uid/:uid/export/posts', middleware.checkAccountPermissions, controllers.user.exportPosts);
|
router.get('/user/uid/:userslug/export/posts', middleware.checkAccountPermissions, middleware.exposeUid, controllers.user.exportPosts);
|
||||||
router.get('/user/uid/:uid/export/uploads', middleware.checkAccountPermissions, controllers.user.exportUploads);
|
router.get('/user/uid/:userslug/export/uploads', middleware.checkAccountPermissions, middleware.exposeUid, controllers.user.exportUploads);
|
||||||
router.get('/user/uid/:uid/export/profile', middleware.checkAccountPermissions, controllers.user.exportProfile);
|
router.get('/user/uid/:userslug/export/profile', middleware.checkAccountPermissions, middleware.exposeUid, controllers.user.exportProfile);
|
||||||
|
|
||||||
router.get('/:type/pid/:id', controllers.api.getObject);
|
router.get('/:type/pid/:id', controllers.api.getObject);
|
||||||
router.get('/:type/tid/:id', controllers.api.getObject);
|
router.get('/:type/tid/:id', controllers.api.getObject);
|
||||||
|
|||||||
@@ -1160,6 +1160,33 @@ describe('Controllers', function () {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should export users posts', function (done) {
|
||||||
|
request(nconf.get('url') + '/api/user/uid/foo/export/posts', { jar: jar }, function (err, res, body) {
|
||||||
|
assert.ifError(err);
|
||||||
|
assert.equal(res.statusCode, 200);
|
||||||
|
assert(body);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export users uploads', function (done) {
|
||||||
|
request(nconf.get('url') + '/api/user/uid/foo/export/uploads', { jar: jar }, function (err, res, body) {
|
||||||
|
assert.ifError(err);
|
||||||
|
assert.equal(res.statusCode, 200);
|
||||||
|
assert(body);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export users profile', function (done) {
|
||||||
|
request(nconf.get('url') + '/api/user/uid/foo/export/profile', { jar: jar }, function (err, res, body) {
|
||||||
|
assert.ifError(err);
|
||||||
|
assert.equal(res.statusCode, 200);
|
||||||
|
assert(body);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should load notifications page', function (done) {
|
it('should load notifications page', function (done) {
|
||||||
var notifications = require('../src/notifications');
|
var notifications = require('../src/notifications');
|
||||||
var notifData = {
|
var notifData = {
|
||||||
|
|||||||
@@ -87,6 +87,24 @@ describe('Upload Controllers', function () {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should upload an image to a post and then delete the upload', function (done) {
|
||||||
|
helpers.uploadFile(nconf.get('url') + '/api/post/upload', path.join(__dirname, '../test/files/test.png'), {}, jar, csrf_token, function (err, res, body) {
|
||||||
|
assert.ifError(err);
|
||||||
|
assert.equal(res.statusCode, 200);
|
||||||
|
assert(Array.isArray(body));
|
||||||
|
assert(body[0].url);
|
||||||
|
var name = body[0].url.replace(nconf.get('upload_url'), '');
|
||||||
|
socketUser.deleteUpload({ uid: regularUid }, { uid: regularUid, name: name }, function (err) {
|
||||||
|
assert.ifError(err);
|
||||||
|
db.getSortedSetRange('uid:' + regularUid + ':uploads', 0, -1, function (err, uploads) {
|
||||||
|
assert.ifError(err);
|
||||||
|
assert.equal(uploads.includes(name), false);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should resize and upload an image to a post', function (done) {
|
it('should resize and upload an image to a post', function (done) {
|
||||||
var oldValue = meta.config.maximumImageWidth;
|
var oldValue = meta.config.maximumImageWidth;
|
||||||
meta.config.maximumImageWidth = 10;
|
meta.config.maximumImageWidth = 10;
|
||||||
|
|||||||
Reference in New Issue
Block a user