text:
'use strict';

/**
 * Ensure that the connection is made to the test database
 */
var mongoose = require('gebo-mongoose-connection').get(true);

var actionModule = require('..');

// Stores the various object IDs created in the setUps
var _id;

/**
 * createBlog
 */
exports.createBlog = {
    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should add a new blog to the database for an authorized agent': function(test) {
        test.expect(3);

        // Make sure there are no blogs in the database
        actionModule.schemata.blogModel.find({}, function(err, blogs) {
            if (err) {
              console.log(err);
            }
            test.equal(blogs.length, 0);
            actionModule.actions.createBlog({ resource: 'blogs', write: true },
                                            { content: { title: 'My cool new blog' } }).
                then(function(blog) {
                    test.equal(blog.title, 'My cool new blog');
                    test.ok(!!blog._id);
                    test.done();
                  }).
                catch(function(err) {
                    test.ok(false, err);
                    test.done();
                  });
          });
    },

    'Should add a new blog to the database for an admin': function(test) {
        test.expect(3);

        // Make sure there are no blogs in the database
        actionModule.schemata.blogModel.find({}, function(err, blogs) {
            if (err) {
              console.log(err);
            }
            test.equal(blogs.length, 0);
            actionModule.actions.createBlog({ resource: 'blogs', admin: true },
                                            { content: { title: 'My cool new blog' } }).
                then(function(blog) {
                    test.equal(blog.title, 'My cool new blog');
                    test.ok(!!blog._id);
                    test.done();
                  }).
                catch(function(err) {
                    test.ok(false, err);
                    test.done();
                  });
          });
    },

    'Should not add a new blog to the database if agent\'s not authorized': function(test) {
        test.expect(1);
        actionModule.actions.createBlog({ resource: 'blogs' },
                                        { content: { title: 'My cool new blog' } }).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the blog title not is not specified': function(test) {
        test.expect(1);
        actionModule.actions.createBlog({ resource: 'blogs', write: true }, {}).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You didn\'t title your new blog');
                test.done();
              });
    },
};

/**
 * deleteBlog
 */
exports.deleteBlog = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            _id = savedBlog._id;
            callback();
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should remove a blog from the database for an authorized agent': function(test) {
        test.expect(2);

        actionModule.actions.deleteBlog({ resource: 'blogs', write: true },
                                        { content: { id: _id} }).
            then(function(ack) {
                test.ok(ack);
                // Make sure the collection is empty
                actionModule.schemata.blogModel.find({}, function(err, blogs) {
                    test.equal(blogs.length, 0);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should remove a blog from the database for an admin': function(test) {
        test.expect(2);

        actionModule.actions.deleteBlog({ resource: 'blogs', admin: true },
                                        { content: { id: _id} }).
            then(function(ack) {
                test.ok(ack);
                // Make sure the collection is empty
                actionModule.schemata.blogModel.find({}, function(err, blogs) {
                    test.equal(blogs.length, 0);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should not delete a blog if the agent\'s not authorized': function(test) {
        test.expect(1);
        actionModule.actions.deleteBlog({ resource: 'blogs' },
                                        { content: { title: 'My cool new blog' } }).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the blog id is not specified': function(test) {
        test.expect(1);
        actionModule.actions.deleteBlog({ resource: 'blogs', write: true }, {}).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You didn\'t specify which blog you want to turf');
                test.done();
              });
    },
};

/**
 * savePost
 */
exports.savePost = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            _id = savedBlog._id;
            callback();
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should add a document to the blog collection for an authorized agent': function(test) {
        test.expect(13);

        actionModule.actions.savePost({ resource: 'blogs', write: true },
                                      { content: {
                                                     blogId: _id,
                                                     headline: 'My cat\'s breath smells like cat food',
                                                     byline: 'Ralph Wiggum',
                                                 }
                                      }).
            then(function(post) {
                test.equal(post.blogId.toString(), _id.toString());
                test.equal(post.headline, 'My cat\'s breath smells like cat food');
                test.equal(post.byline, 'Ralph Wiggum');
                test.ok(!!post.date);
                test.equal(post.published, false);
                test.equal(post.commentsAllowed, false);

                // Make sure the post has been saved
                actionModule.schemata.postModel.find({}, function(err, post) {
                    test.equal(post.length, 1);
                    test.equal(post[0].blogId.toString(), _id.toString());
                    test.equal(post[0].headline, 'My cat\'s breath smells like cat food');
                    test.equal(post[0].byline, 'Ralph Wiggum');
                    test.ok(!!post[0].date);
                    test.equal(post[0].published, false);
                    test.equal(post[0].commentsAllowed, false);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should overwrite existing post if post ID already exists': function(test) {
        test.expect(15);
        actionModule.actions.savePost({ resource: 'blogs', write: true },
                                      { content: {
                                                     blogId: _id,
                                                     headline: 'My cat\'s breath smells like cat food',
                                                     byline: 'Ralph Wiggum',
                                                 }
                                      }).
            then(function(post) {
                test.equal(post.blogId.toString(), _id.toString());
                test.equal(post.headline, 'My cat\'s breath smells like cat food');
                test.equal(post.byline, 'Ralph Wiggum');
                test.ok(!!post.date);
                test.equal(post.published, false);
                test.equal(post.commentsAllowed, false);

                // Make sure the post has been saved
                actionModule.schemata.postModel.find({}, function(err, posts) {
                    test.equal(posts.length, 1);
                    test.equal(posts[0].headline, 'My cat\'s breath smells like cat food');

                    // Attempt to update the post
                    actionModule.actions.savePost({ resource: 'blogs', write: true },
                                                  { content: {
                                                                 _id: post._id,
                                                                 headline: 'My dog\'s breath smells like cat food',
                                                                 published: true,
                                                                 commentsAllowed: true,
                                                             }
                                                  }).
                        then(function(post) {
                            actionModule.schemata.postModel.find({}, function(err, updatedPosts) {
                                test.equal(updatedPosts.length, 1);
                                test.equal(updatedPosts[0].blogId.toString(), _id.toString());
                                test.equal(updatedPosts[0].headline, 'My dog\'s breath smells like cat food');
                                test.equal(updatedPosts[0].byline, 'Ralph Wiggum');
                                test.ok(!!updatedPosts[0].date);
                                test.equal(updatedPosts[0].published, true);
                                test.equal(updatedPosts[0].commentsAllowed, true);
                                test.done();
                              });
                          }).
                        catch(function(err) {
                            test.ok(false, err);
                            test.done();
                          });
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should add a document to the blog collection for an admin': function(test) {
        test.expect(13);

        actionModule.actions.savePost({ resource: 'blogs', admin: true },
                         { content: {
                                        blogId: _id,
                                        headline: 'My cat\'s breath smells like cat food',
                                        byline: 'Ralph Wiggum',
                                    }
                         }).
            then(function(post) {
                test.equal(post.blogId.toString(), _id.toString());
                test.equal(post.headline, 'My cat\'s breath smells like cat food');
                test.equal(post.byline, 'Ralph Wiggum');
                test.ok(!!post.date);
                test.equal(post.published, false);
                test.equal(post.commentsAllowed, false);

                // Make sure the post has been saved
                actionModule.schemata.postModel.find({}, function(err, post) {
                    test.equal(post.length, 1);
                    test.equal(post[0].blogId.toString(), _id.toString());
                    test.equal(post[0].headline, 'My cat\'s breath smells like cat food');
                    test.equal(post[0].byline, 'Ralph Wiggum');
                    test.ok(!!post[0].date);
                    test.equal(post[0].published, false);
                    test.equal(post[0].commentsAllowed, false);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should not save a document to the collection if not authorized': function(test) {
        test.expect(1);
        actionModule.actions.savePost({ resource: 'blogs' },
                         { content: { headline: 'My cat\'s breath smells like cat food' } }).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post isn\'t included in the message contents': function(test) {
        test.expect(1);
        actionModule.actions.savePost({ resource: 'blogs', write: true }, {}).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'Where\'s the post? You\'re missing something');
                test.done();
              });
    },
};

/**
 * deletePost
 */
exports.deletePost = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            actionModule.actions.savePost({ resource: 'blogs', admin: true },
                             { content: {
                                            blogId: _id,
                                            headline: 'My cat\'s breath smells like cat food',
                                            byline: 'Ralph Wiggum',
                                        }
                             }).
                then(function(post) {
                    _id = post._id;
                    callback();
                  }).
                catch(function(err) {
                    console.log(err);
                    callback();
                  });
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should delete the post from the database for an authorized user': function(test) {
        test.expect(2);
        actionModule.actions.deletePost({ resource: 'blogs', write: true },
                           { content: { id: _id } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.find({}, function(err, posts) {
                    test.equal(posts.length, 0);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should delete the post from the database for an admin': function(test) {
        test.expect(2);
        actionModule.actions.deletePost({ resource: 'blogs', admin: true },
                           { content: { id: _id } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.find({}, function(err, posts) {
                    test.equal(posts.length, 0);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should do nothing for an unauthorized agent': function(test) {
        test.expect(1);
        actionModule.actions.deletePost({ resource: 'blogs' },
                           { content: { id: _id } }).
            then(function(ack) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post\'s ID is not included in the message content': function(test) {
        test.expect(1);
        actionModule.actions.deletePost({ resource: 'blogs', write: true }, {}).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.ok(false, 'Shouldn\'t get here');
                    test.done();
                  });
              }).
            catch(function(err) {
                test.equal(err, 'Which post do you want to delete?');
                test.done();
              });
    },
};

/**
 * publishPost
 */
exports.publishPost = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            actionModule.actions.savePost({ resource: 'blogs', admin: true },
                             { content: {
                                            blogId: _id,
                                            headline: 'My cat\'s breath smells like cat food',
                                            byline: 'Ralph Wiggum',
                                        }
                             }).
                then(function(post) {
                    _id = post._id;
                    callback();
                  }).
                catch(function(err) {
                    console.log(err);
                    callback();
                  });
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should set the post\'s published flag to true for an authorized user': function(test) {
        test.expect(3);
        actionModule.actions.publishPost({ resource: 'blogs', write: true },
                            { content: { id: _id, published: true } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.ok(post.published);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should set the post\'s published flag to true for an admin': function(test) {
        test.expect(3);
        actionModule.actions.publishPost({ resource: 'blogs', write: true },
                            { content: { id: _id, published: true } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.ok(post.published);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should do nothing for an unauthorized agent': function(test) {
        test.expect(1);
        actionModule.actions.publishPost({ resource: 'blogs' },
                            { content: { id: _id, published: true } }).
            then(function(ack) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post\'s ID is not included in the message content': function(test) {
        test.expect(1);
        actionModule.actions.publishPost({ resource: 'blogs', write: true }, {}).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.ok(false, 'Shouldn\'t get here');
                    test.done();
                  });
              }).
            catch(function(err) {
                test.equal(err, 'Which post do you want to publish?');
                test.done();
              });
    },
};

/**
 * unpublishPost
 *
 * This is just publishPost, but with the published flag set to false
 */
exports.unpublishPost = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            actionModule.actions.savePost({ resource: 'blogs', admin: true },
                             { content: {
                                            blogId: _id,
                                            headline: 'My cat\'s breath smells like cat food',
                                            byline: 'Ralph Wiggum',
                                            published: true,
                                        }
                             }).
                then(function(post) {
                    _id = post._id;
                    callback();
                  }).
                catch(function(err) {
                    console.log(err);
                    callback();
                  });
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should set the post\'s published flag to false for an authorized user': function(test) {
        test.expect(3);
        actionModule.actions.publishPost({ resource: 'blogs', write: true },
                            { content: { id: _id, published: false } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.equal(post.published, false);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should set the post\'s published flag to false for an admin': function(test) {
        test.expect(3);
        actionModule.actions.publishPost({ resource: 'blogs', write: true },
                            { content: { id: _id, published: false } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.equal(post.published, false);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should do nothing for an unauthorized agent': function(test) {
        test.expect(1);
        actionModule.actions.publishPost({ resource: 'blogs' },
                            { content: { id: _id, published: false } }).
            then(function(ack) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post\'s ID is not included in the message content': function(test) {
        test.expect(1);
        actionModule.actions.publishPost({ resource: 'blogs', write: true }, {}).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.ok(false, 'Shouldn\'t get here');
                    test.done();
                  });
              }).
            catch(function(err) {
                test.equal(err, 'Which post do you want to publish?');
                test.done();
              });
    },
};

/**
 * saveComment
 */
exports.saveComment = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            actionModule.actions.savePost({ resource: 'blogs', admin: true },
                             { content: {
                                            blogId: _id,
                                            headline: 'My cat\'s breath smells like cat food',
                                            byline: 'Ralph Wiggum',
                                            published: true,
                                        }
                             }).
                then(function(post) {
                    _id = post._id;
                    callback();
                  }).
                catch(function(err) {
                    console.log(err);
                    callback();
                  });
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should save a document to the comment collection for an authorized agent': function(test) {
        test.expect(9);

        actionModule.actions.saveComment({ resource: 'blogs', write: true },
                            { content: {
                                           postId: _id,
                                           byline: 'Chief Wiggum',
                                           body: 'That\'s right, Ralphy',
                                       }
                            }).
            then(function(comment) {
                test.equal(comment.postId.toString(), _id.toString());
                test.equal(comment.byline, 'Chief Wiggum');
                test.equal(comment.body, 'That\'s right, Ralphy');
                test.ok(!!comment.date);

                // Make sure the post has been saved
                actionModule.schemata.commentModel.find({}, function(err, comment) {
                    test.equal(comment.length, 1);
                    test.equal(comment[0].postId.toString(), _id.toString());
                    test.equal(comment[0].byline, 'Chief Wiggum');
                    test.equal(comment[0].body, 'That\'s right, Ralphy');
                    test.ok(!!comment[0].date);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should save a document to the comment collection for an admin': function(test) {
        test.expect(9);

        actionModule.actions.saveComment({ resource: 'blogs', write: true },
                            { content: {
                                           postId: _id,
                                           byline: 'Chief Wiggum',
                                           body: 'That\'s right, Ralphy',
                                       }
                            }).
            then(function(comment) {
                test.equal(comment.postId.toString(), _id.toString());
                test.equal(comment.byline, 'Chief Wiggum');
                test.equal(comment.body, 'That\'s right, Ralphy');
                test.ok(!!comment.date);

                // Make sure the post has been saved
                actionModule.schemata.commentModel.find({}, function(err, comment) {
                    test.equal(comment.length, 1);
                    test.equal(comment[0].postId.toString(), _id.toString());
                    test.equal(comment[0].byline, 'Chief Wiggum');
                    test.equal(comment[0].body, 'That\'s right, Ralphy');
                    test.ok(!!comment[0].date);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should not save a document to the collection if not authorized': function(test) {
        test.expect(1);
        actionModule.actions.saveComment({ resource: 'blogs' },
                            { content: {
                                           postId: _id,
                                           byline: 'Chief Wiggum',
                                           body: 'That\'s right, Ralphy',
                                       }
                            }).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post isn\'t included in the message contents': function(test) {
        test.expect(1);
        actionModule.actions.saveComment({ resource: 'blogs', write: true }, {}).
            then(function(blog) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'Upon what are you commenting? You\'re missing something');
                test.done();
              });
    },
};

/**
 * deleteComment
 */
exports.deleteComment = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            actionModule.actions.savePost({ resource: 'blogs', admin: true },
                             { content: {
                                            blogId: savedBlog._id,
                                            headline: 'My cat\'s breath smells like cat food',
                                            byline: 'Ralph Wiggum',
                                            published: true,
                                        }
                             }).
                then(function(post) {
                    actionModule.actions.saveComment({ resource: 'blogs', admin: true },
                                        { content: {
                                                       postId: post._id,
                                                       byline: 'Chief Wiggum',
                                                       body: 'That\'s right, Ralphy',
                                                   }
                                        }).
                        then(function(comment) {
                            _id = comment._id;
                            callback();
                          }).
                        catch(function(err) {
                            console.log(err);
                            callback();
                          });
                  }).
                catch(function(err) {
                    console.log(err);
                    callback();
                  });
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should delete the comment from the collection for an authorized user': function(test) {
        test.expect(2);
        actionModule.actions.deleteComment({ resource: 'blogs', write: true },
                              { content: { id: _id } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.commentModel.find({}, function(err, comments) {
                    test.equal(comments.length, 0);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should delete the comment from the collection for an admin': function(test) {
        test.expect(2);
        actionModule.actions.deleteComment({ resource: 'blogs', admin: true },
                              { content: { id: _id } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.commentModel.find({}, function(err, comments) {
                    test.equal(comments.length, 0);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should do nothing for an unauthorized agent': function(test) {
        test.expect(1);
        actionModule.actions.deleteComment({ resource: 'blogs' },
                              { content: { id: _id } }).
            then(function(ack) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post\'s ID is not included in the message content': function(test) {
        test.expect(1);
        actionModule.actions.deleteComment({ resource: 'blogs', write: true }, {}).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.ok(false, 'Shouldn\'t get here');
                    test.done();
                  });
              }).
            catch(function(err) {
                test.equal(err, 'Which comment do you want to delete?');
                test.done();
              });
    },
};

/**
 * allowComments
 */
exports.allowComments = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            actionModule.actions.savePost({ resource: 'blogs', admin: true },
                             { content: {
                                            blogId: _id,
                                            headline: 'My cat\'s breath smells like cat food',
                                            byline: 'Ralph Wiggum',
                                        }
                             }).
                then(function(post) {
                    _id = post._id;
                    callback();
                  }).
                catch(function(err) {
                    console.log(err);
                    callback();
                  });
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should set the post\'s published flag to true for an authorized user': function(test) {
        test.expect(3);
        actionModule.actions.allowComments({ resource: 'blogs', write: true },
                              { content: { id: _id, allow: true } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.ok(post.commentsAllowed);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should set the post\'s published flag to true for an admin': function(test) {
        test.expect(3);
        actionModule.actions.allowComments({ resource: 'blogs', admin: true },
                              { content: { id: _id, allow: true } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.ok(post.commentsAllowed);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should do nothing for an unauthorized agent': function(test) {
        test.expect(1);
        actionModule.actions.allowComments({ resource: 'blogs' },
                              { content: { id: _id, allow: true } }).
            then(function(ack) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post\'s ID is not included in the message content': function(test) {
        test.expect(1);
        actionModule.actions.allowComments({ resource: 'blogs', write: true }, {}).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.ok(false, 'Shouldn\'t get here');
                    test.done();
                  });
              }).
            catch(function(err) {
                test.equal(err, 'On which post do you want to modify commenting?');
                test.done();
              });
    },
};

/**
 * disallowComments
 *
 * This is just allowComments with the allow property set to false
 */
exports.disallowComments = {

    setUp: function(callback) {
        var blog = new actionModule.schemata.blogModel({ title: 'Deep thoughts...' });
        blog.save(function(err, savedBlog) {
            if (err) {
              console.log(err);
            }
            actionModule.actions.savePost({ resource: 'blogs', admin: true },
                             { content: {
                                            blogId: _id,
                                            headline: 'My cat\'s breath smells like cat food',
                                            byline: 'Ralph Wiggum',
                                            commentsAllowed: true,
                                        }
                             }).
                then(function(post) {
                    _id = post._id;
                    callback();
                  }).
                catch(function(err) {
                    console.log(err);
                    callback();
                  });
          });
    },

    tearDown: function(callback) {
        actionModule.schemata.connection.db.dropDatabase(function(err) {
            if (err) {
              console.log(err);
            }
            callback();
          });
    },

    'Should set the post\'s commentsAllowed flag to true for an authorized user': function(test) {
        test.expect(3);
        actionModule.actions.allowComments({ resource: 'blogs', write: true },
                              { content: { id: _id, allow: false } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.equal(post.commentsAllowed, false);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should set the post\'s commentsAllowed flag to true for an admin': function(test) {
        test.expect(3);
        actionModule.actions.allowComments({ resource: 'blogs', admin: true },
                              { content: { id: _id, allow: false } }).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.equal(post.headline, 'My cat\'s breath smells like cat food');
                    test.equal(post.commentsAllowed, false);
                    test.done();
                  });
              }).
            catch(function(err) {
                test.ok(false, err);
                test.done();
              });
    },

    'Should do nothing for an unauthorized agent': function(test) {
        test.expect(1);
        actionModule.actions.allowComments({ resource: 'blogs' },
                              { content: { id: _id, allow: false } }).
            then(function(ack) {
                test.ok(false, 'Shouldn\'t get here');
                test.done();
              }).
            catch(function(err) {
                test.equal(err, 'You are not permitted to request or propose that action');
                test.done();
              });
    },

    'Should not barf if the post\'s ID is not included in the message content': function(test) {
        test.expect(1);
        actionModule.actions.allowComments({ resource: 'blogs', write: true }, {}).
            then(function(ack) {
                test.ok(ack);
                actionModule.schemata.postModel.findById(_id, function(err, post) {
                    test.ok(false, 'Shouldn\'t get here');
                    test.done();
                  });
              }).
            catch(function(err) {
                test.equal(err, 'On which post do you want to modify commenting?');
                test.done();
              });
    },
};


text:
package io.circe

import io.circe.tests.CirceMunitSuite

/**
 * On the JVM this trait contains tests that fail because of bugs (or at least
 * limitations) on Scala.js.
 */
trait LargeNumberDecoderTests { this: CirceMunitSuite => }
trait LargeNumberDecoderTestsMunit { this: CirceMunitSuite => }

redpajama_set_name: RedPajamaGithub


text:
<?xml version="1.0" encoding="UTF-8"?>
<ldswebml type="image" uri="/media-library/images/primary/line-art#john-baptizing-jesus-377623" xml:lang="eng" locale="eng" status="publish">
  <search-meta>
      <uri-title its:translate="no" xmlns:its="http://www.w3.org/2005/11/its">john-baptizing-jesus-377623</uri-title>
      <source>john-baptizing-jesus-377623</source>
      <publication-type its:translate="no" xmlns:its="http://www.w3.org/2005/11/its">image</publication-type>
      <media-type its:translate="no" xmlns:its="http://www.w3.org/2005/11/its">image</media-type>
      <publication value="ldsorg">LDS.org</publication>
      <publication-date value="2012-04-09">2012-04-09</publication-date>
      <title/>
      <description/>
      <collections>
          <collection its:translate="no" xmlns:its="http://www.w3.org/2005/11/its">global-search</collection>
          <collection its:translate="no" xmlns:its="http://www.w3.org/2005/11/its">media</collection>
          <collection its:translate="no" xmlns:its="http://www.w3.org/2005/11/its">images</collection>
      </collections>
      <subjects>
          <subject>jesus</subject>
          <subject>baptized</subject>
          <subject>baptism</subject>
          <subject>john</subject>
          <subject>baptist</subject>
          <subject>jordan</subject>
          <subject>river</subject>
          <subject>coloring</subject>
          <subject>pages</subject>
          <subject>activity</subject>
          <subject>activities</subject>
      </subjects>
  </search-meta>
  <no-search>
      <path>http://media.ldscdn.org/images/media-library/primary/line-art/john-baptizing-jesus-377623-gallery.jpg</path>
      <images>
          http://media.ldscdn.org/images/media-library/primary/line-art/john-baptizing-jesus-377623-thumbnail.jpg
      </images>
          <download-urls>
              <download-url>
                  Mobile
                  <size>223 KB</size>
                  <path>http://media.ldscdn.org/images/media-library/primary/line-art/john-baptizing-jesus-377623-mobile.jpg</path>
              </download-url>
              <download-url>
                  Tablet
                  <size>293 KB</size>
                  <path>http://media.ldscdn.org/images/media-library/primary/line-art/john-baptizing-jesus-377623-tablet.jpg</path>
              </download-url>
              <download-url>
                  Print
                  <size>575 KB</size>
                  <path>http://media.ldscdn.org/images/media-library/primary/line-art/john-baptizing-jesus-377623-print.jpg</path>
              </download-url>
              <download-url>
                  Wallpaper
                  <size>670 KB</size>
                  <path>http://media.ldscdn.org/images/media-library/primary/line-art/john-baptizing-jesus-377623-wallpaper.jpg</path>
              </download-url>
          </download-urls>
  </no-search>
<ldse-meta its:translate="no" xmlns="http://lds.org/code/lds-edit" xmlns:its="http://www.w3.org/2005/11/its"><document id="john-baptizing-jesus-377623" locale="eng" uri="/media-library/images/primary/line-art#john-baptizing-jesus-377623" status="publish" site="ldsorg" source="chq" words="138" tgp="0.4825"/><created username="lds-edit" userid=""/><last-modified date="2012-05-10T12:26:12.550235-06:00" username="lds-edit" userid=""/></ldse-meta></ldswebml>


text:
require 'uri'
module SolrQuery

  # The abstract superclass for different types of solr queries.
  #
  # We're really overloading this class to be either a leaf node
  # (with an actual query) or an internal node (with an operator and one
  # or two child notes, each of which might also be either a leaf or a
  # tree)

  class AbstractQuery

    # For a leaf, the tokens to seach on. Could be compled (e.g., with quotes)
    attr_accessor :search

    # A hash mapping 'solrfield' => boost.
    attr_accessor :fields

    # How much to boost this particular query (leaf or tree)
    attr_accessor :boost

    # The operator (AND/OR/NOT)
    attr_accessor :op

    # The left side of the binary operator (AND/OR)
    attr_accessor :left

    # The right side of the binary operator (AND/OR/NOT)
    attr_accessor :right

    # Local parameters
    attr_accessor :lp

    ##
    # Initialize the query object.
    #
    # @option opts [String] :search The query string
    # @option opts [Hash] :fields A set of 'solrfield'=>'boost' pairs
    # @option opts [Float] :boost The boost for this whole query
    # @return [AbstractQuery or subclass] The new query object.
    def initialize opts={}
      @tokens = opts[:search]
      @fields = opts[:fields] || {}
      @boost = opts[:boost]
      @type = "must_be_overridden"
      @lp = {} # the local params
    end

    # Take a hash that maps termstring to URL arguments and return
    # a string that will go in the URL (not yet URL-encoded) based on it
    # for this query type. The reason to use the termhash is so you can have
    # multiple queries all using the same terms, e.g.
    #     http://...?q=_query_:"{!lucene df='author1' v=$q1}" OR _query_:"{!lucene df='author2' v=$q1}"&q1=my search terms
    #
    # This default method takes care of anything in the @lp (localParams) and a basic boost
    #
    # Everything in the termhash gets turned into URL components, so if you need to stick extra
    # stuff in there, you can (for, e.g., boost queries)
    #
    # @param [Hash] termhash A hash mapping search strings to q1/q2/etc. -- the output of
    # self.terms

    def leafnode termhash
      b = @boost? '^' + @boost.to_s : ''
      id = termhash[@tokens]

      args = @lp.each.map{|k,v| "#{k}='#{v}'"}.join(' ')

      args = ' ' + args if args != ''
      return "_query_:\"{!#{@type}#{args} v=$#{id}}\"#{b}"
    end

    # In the default case (inner == false) on a tree, walk the query tree and get a hash of
    # token strings (the actual queries, as opposed to the fields, booleans, etc.).
    # mapped to arbitrary identifiers (in this implementation, q1, q2, q3, ...)]
    #
    # In the recursive call (inner == true) on tree, walk the tree and build
    # up a (nonunique) array of tokenstrings. This is what the nonrecursive call
    # deduplicates and turns into the eventual return Hash.
    #
    # Called against a leaf node, just return the tokenstring(s) from the leaf
    #
    # Basically, call it with inner==false on the node you want to
    # get the termlist for.
    #
    # @param [Boolean] inner Flag indicating whether this is a top-level call (inner == false)
    # or a recursive call (inner == true)
    # return [Hash, Array] Either an array of tokenstring (inner==true) or a hash mapping
    # arbitrary ids (q1,q2) to those tokenstrings

    def terms inner = nil
      t = []
      if @op
        if @left
          t += @left.terms(true) + @right.terms(true)
        else
          t += @right.terms(true)
        end
      else
        t = self.leafterms
      end

      if inner
        return t
      else
        t = t.compact.uniq
        rv = {}
        t.each_with_index do |v, i|
          rv[v] = "q#{i}"
        end
        return rv
      end
    end

    # Return the set of tokenstrings for this leaf node
    # @return [Array<String>] The tokenstrings for this node
    def leafterms
      return [@tokens]
    end

    # Combine the current query with another via the passed operator
    # @param ["AND", "OR", "NOT"] op The operator
    # @return [AbstractQuery] The new query

    def conjoin op, other
      nq = self.class.new
      nq.op = op
      if other
        nq.left = self
        nq.right = other
      else
        nq.right = self
      end
      return nq
    end

    # Unary NOT of this query (the -@ is ruby magic for a leading minus sign, e.g. '-q')
    def -@
      return self.conjoin 'NOT', nil
    end
    alias_method :not, :-@

    # Boolean NOT for two queries
    def - other
      self.conjoin 'NOT', other
    end
    alias_method :not, :-

    # Boolean AND of two queries
    def & other
      self.conjoin 'AND', other
    end
    alias_method :and, :&

    # Boolean OR of two queries
    def | other
      self.conjoin 'OR', other
    end
    alias_method :or, :|

    # A string suitable for dropping onto the end of a solr URL to do the query
    #
    # @return [String] an already-URI-encoded string of the form q=_query_:"..."&q1=term2 term3&...
    def as_URL_snippet
      return self.query.map{|k,v| "#{k}=>#{URI.escape(v)}"}.join('&')
    end

    # The query is a hash that includes both the q parameter and all the id=>tokenstring
    # pairs.
    # @return [Hash] A hash of the form {q=>"<long query>", q1=>"tokenstring1", ...}
    def query
      rv = {'q' => query_without_terms}
      self.terms.each_pair do |val, arg|
        rv[arg] = val
      end
      return rv
    end

    # The full query with the tokenstrings replaced by the appropriate
    # q1, q2, etc. You end up with something like
    #  _query_:"{!lucene val=q1} AND {!dismax ...}"
    #
    # @param [Hash] terms The mapping of q1/q2/... to tokenstrings

    def query_without_terms terms=self.terms

      b = @boost? '^' + @boost.to_s : ''

      if @op
        if @left
          return "(#{@left.query_without_terms terms} #{@op} #{@right.query_without_terms terms})#{b}"
        else
          return "(#{@op} #{right.query_without_terms terms})#{b}"
        end
      else
        return self.leafnode(terms)
      end
    end
  end

  class Lucene < AbstractQuery

    # The default operator ('AND' or 'OR'). Default is 'AND'

    # The default field to search
    attr_accessor :defaultField
    alias_method :field, :defaultField
    alias_method :field=, :defaultField=

    # Get a new object as per AbstractQuery#initialize and set the type
    # to 'lucene'
    #
    # In addition to the standard parameters, also allow :defaultOp to set
    # the default operator to AND/OR
    #
    # If the fields hash has more than one entry, go ahead and build up
    # the complex query tree with the defaultOp
    #
    # @option opts [String] :search The query string
    # @option opts [String] :fields The field to search on
    # @option opts [Float] :boost The boost for this whole query
    # @Option opts ["AND", 'and', :and, 'OR', 'or', :or] :defaultOp The default operator
    # @return [Lucene] The new query object.object (or tree)

    def initialize opts={}
      super
      @type = "lucene"
      @defaultOp = opts[:defaultOp] || 'AND'
      @defaultField = opts[:defaultField] || opts[:field]

      # build up a complex query
    end

    # Set the default field, if defined, and kick it up to AbstractQuery
    def leafnode termhash
      # Should never have a compound fields hash
      @lp['df'] = @defaultField if @defaultField

      # Override with passed field if there was one
      field,boost = @fields.first
      if field
        @lp['df'] = field
      end

      super
    end

    def defaultOp
      return @lp['q.op']
    end

    def defaultOp= val
      raise ArgumentError, "Must be 'AND' or 'OR'" unless %w(AND OR).include? val
      @lp['q.op'] = val
    end
  end

  # A dismax query is different in that instead of taking a single field, it takes
  # multiple field/boosts and multiple pf/boosts

  class DisMax < AbstractQuery

    attr_accessor :fields, :pf

    def initialize tokens=nil, fields={}, pf = {}
      @tokens = tokens
      @fields = fields
      @pf = pf
      @type = 'dismax'
      @lp = {}
    end

    def leafnode termhash
      @lp['qf'] = fields.each_pair.map {|k,v| "#{k}^#{v}"}.join(' ') if fields.size > 0
      @lp['pf'] = pf.each_pair.map {|k,v| "#{k}^#{v}"}.join(' ') if pf.size > -0
      # do something with boost query
      super
    end
  end

end


text:
from django.test import TestCase
from django.urls import reverse
from django.contrib.auth.hashers import make_password
from model_mommy import mommy

from .forms import RegistrationForm
from .models import User

class UserManager(TestCase):
    def test_create_user(self):
        user = User.objects.create_user("jonnyrico@fednet.gov", password="iwanttoknowmore")
        User.objects.get(id=user.id)

class RegistrationTest(TestCase):
    def setUp(self):
        self.user = mommy.prepare_recipe('gregazevedo.account.user')
        self.form_keys = RegistrationForm.base_fields.keys()
        self.form_data = {k: v for (k, v) in self.user.__dict__.items() if k in self.form_keys}
        self.form_data['tos'] = "True"
        self.form_data['password1'] = self.form_data['password2'] = "bugssuck"

    def test_user_registration_fails(self):
        """
        on failed registration, keep the user on the same page and ask for a fix
        """
        del self.form_data['tos']
        url = reverse("register")
        response = self.client.post(url, self.form_data)
        actual = response.status_code
        expected = 200
        self.assertEqual(actual, expected)

    def test_user_registration_fails_passwords_must_match(self):
        self.form_data['password2'] = "bugs rule"

        url = reverse("register")
        response = self.client.post(url, self.form_data)
        actual = response.status_code
        expected = 200
        self.assertEqual(actual, expected)
        actual = response.context['form'].errors['__all__']
        expected = ["The two password fields didn't match."]
        self.assertEqual(actual, expected)

    def test_user_registration_fails_unique_email(self):
        url = reverse("register")
        actual = self.client.post(url, self.form_data)
        expected = reverse("home")
        self.assertRedirects(actual, expected)
        User.objects.get(email=self.user.email)
        response = self.client.post(url, self.form_data)
        actual = response.status_code
        expected = 200
        self.assertEqual(actual, expected)
        actual = response.context['form'].errors['email']
        expected = ["This email address is already in use. Please supply a different email address."]
        self.assertEqual(actual, expected)

    def test_user_registration_works(self):
        """
        on successful registration, move user to either
        their profile page or the next page specified in the querystring
        """
        url = reverse("register")
        actual = self.client.post(url, self.form_data)
        expected = reverse("home")
        self.assertRedirects(actual, expected)
        User.objects.get(email=self.user.email)

class LoginTest(TestCase):
    def setUp(self):
        self.user = mommy.make_recipe('gregazevedo.account.user')
        self.password = "wouldYouLikeToKnowMore"
        self.user.set_password(self.password)
        self.user.save()
        self.form_data = {"username": self.user.email,
                          "password": self.password,
                          }

    def test_user_login_unsuccessful(self):
        """
        on successful registration, keep user on login page
        and show error
        """
        self.form_data['password'] = "bugs rule federation drulz"
        url = reverse("login")
        response = self.client.post(url, self.form_data)
        actual = response.status_code
        expected = 200
        self.assertEqual(actual, expected)
        actual = response.context['form'].errors['__all__']
        expected = ['Please enter a correct email address and password. Note that both fields may be case-sensitive.']
        self.assertEqual(actual, expected)

    def test_login_works(self):
        """
        on attempted login, move user to the special page
        """
        url = reverse('login')
        actual = self.client.post(url, self.form_data)
        expected = reverse("home")
        self.assertRedirects(actual, expected)

    def test_register_login_flow_works(self):
        self.user = mommy.prepare_recipe('gregazevedo.account.user')
        self.form_keys = RegistrationForm.base_fields.keys()
        self.form_data = {k: v for (k, v) in self.user.__dict__.items() if k in self.form_keys}
        self.form_data['tos'] = "True"
        self.form_data['password1'] = self.form_data['password2'] = "bugssuck"
        url = reverse("register")
        actual = self.client.post(url, self.form_data)
        expected = reverse("home")
        self.assertRedirects(actual, expected)

        self.form_data = {"username": self.user.email,
                          "password": "bugssuck",
                          }

        self.client.logout()
        url = reverse('login')
        actual = self.client.post(url, self.form_data)
        expected = reverse("home")
        self.assertRedirects(actual, expected)

class UserAdminTest(TestCase):
    def setUp(self):
        form_data = self.login_form_data = {"username": "ben@coolguy.com",
                                            "password": "yeahman"}

        self.user = mommy.make_recipe('gregazevedo.account.user',
                                      email=form_data['username'],
                                      is_superuser=True,
                                      is_staff=True,
                                      password=make_password(form_data['password']),
        )

        self.client.login(username=self.login_form_data['username'],
                          password=self.login_form_data['password'])

    def test_user_admin_list(self):
        url = reverse("admin:account_user_changelist")
        response = self.client.get(url)
        actual = response.status_code
        expected = 200
        self.assertEqual(actual, expected)

    def test_user_admin_detail(self):
        url = reverse("admin:account_user_change", args=[self.user.id])
        response = self.client.get(url)
        actual = response.status_code
        expected = 200
        self.assertEqual(actual, expected)

    def test_user_admin_add(self):
        url = reverse("admin:account_user_add")

        form_data = { "email": "robertcop@ocp.com",
                      "password1":"deadoraliveyourecomingwithme",
                      "password2":"deadoraliveyourecomingwithme",
        }
        actual = response = self.client.post(url, form_data)
        new_user = User.objects.latest("created")
        self.assertEqual(new_user.email, "robertcop@ocp.com")

        expected = reverse("admin:account_user_change", args=[new_user.id])
        self.assertRedirects(actual, expected)

    def test_user_admin_add_different_passwords(self):
        url = reverse("admin:account_user_add")
        form_data = { "email": "robertcop@ocp.com",
                      "password1":"deadoraliveyourecomingwithme",
                      "password2":"freezecreep",
        }
        response = self.client.post(url, form_data)
        actual = response.context['adminform'].form.errors
        expected = {'password2': ["The two password fields didn't match."]}
        self.assertEqual(actual, expected)

    def test_user_admin_change(self):
        url = reverse("admin:account_user_change", args=[self.user.id])
        form_data = {"email": "ben@coolguy.com",
                     "last_login_0": "2015-05-20",
                     "last_login_1": "03:38:28",
                     }
        actual = response = self.client.post(url, form_data)
        expected = reverse("admin:account_user_changelist")
        self.assertRedirects(actual, expected, target_status_code=302)


text:
namespace System.ServiceModel.Channels
{
    internal interface IMergeEnabledMessageProperty
    {
        bool TryMergeWithProperty(object propertyToMerge);
    }
}


text:
Installation
============

[TOC]

## Vim Plugin

Use [Pathogen][] to install the plugin from your choice of repositories:

    hg clone https://hg.stevelosh.com/splice.vim ~/.vim/bundle/splice
    git clone https://github.com/sjl/splice.vim.git ~/.vim/bundle/splice

[Pathogen]: http://www.vim.org/scripts/script.php?script_id=2332

Build the docs:

    :call pathogen#helptags()

## VCS Support

Once you've installed Splice you'll need to configure your version control
system to use it as a merge tool.

### Mercurial

Add the following lines to `~/.hgrc`:

    [merge-tools]
    splice.executable = mvim
    splice.args = -f $base $local $other $output -c 'SpliceInit'
    splice.premerge = keep
    splice.priority = 1

**Note:** replace `mvim` with `gvim` if you're on Linux, or just plain `vim` if you prefer to keep the editor in the console.

### Git

Add the following lines to `~/.gitconfig`:

    [merge]
    tool = splice

    [mergetool "splice"]
    cmd = "mvim -f $BASE $LOCAL $REMOTE $MERGED -c 'SpliceInit'"
    trustExitCode = true

**Note:** replace `mvim` with `gvim` if you're on Linux, or just plain `vim` if you prefer to keep the editor in the console.

### Bazaar

For Bazaar 2.4 or greater, add the following line to bazaar.conf:

    bzr.mergetool.splice = mvim {base} {this} {other} {result} -c 'SpliceInit'

Optionally, change the default merge tool by setting:

    bzr.default_mergetool = splice

For earlier versions of Bazaar, set the following entry in bazaar.conf:

    external_merge = mvim %b %t %o %r -c 'SpliceInit'

**Note:** replace `mvim` with `gvim` if you're on Linux, or just plain `vim` if you prefer to keep the editor in the console.


text:
layout: post
title: "Getting Started with Programming"
quote: On Monday the 17th of March, I gave an introductory talk about programming, startups, and hackathons.
image: false
video: false
---

[I gave a talk](https://www.facebook.com/events/429304987173203/) on how startups, hackathons and programming are changing the world and the way people look at the tech industry. One of the things I focused most on was the importance of programming.

So, how do you get started with programming?

First thing's first: establish a goal in mind. Do you want to make your own personal website? Do you want to make an app? Do you want to build a robot?

The best place to first look at is [Codecademy](http://codecademy.com/) because it assumes 0 knowledge on all of its courses. They're also pretty interactive and fun to learn.

When it comes to "what languages are best to start with", it really depends on what you intend to do.

##Do you want to make apps?
- The [TheNewBoston.org's Java courses](http://thenewboston.org/list.php?cat=31) are great. Use that to learn Java if you want to make Android apps.
- Stanford University put up their iPhone & iPad App Development courses [online for free on iTunes U](https://itunes.apple.com/us/course/developing-ios-7-apps-for/id733644550). It assumes a little prior programming knowledge.
- A really, really easy language to learn is VB.NET, and you can use it to develop websites and Windows Phone apps. [HomeAndLearn](http://homeandlearn.co.uk/NET/vbNet.html) have a really smooth teaching site.

##Do you want to build websites? (all of these languages can be done in Codecademy)
- The one to rule them all: HTML, CSS and JavaScript, which are three very easy and awesome languages. Combined, you can make pretty epic websites too that work on both desktop and mobile. However, you can do more with other languages that may be difficult to do with JavaScript. Note: HTML and CSS are scripting languages, used to format and style a page, and unlike JavaScript, they are not considered programming languages.
- Ruby is currently one of the easiest and most effective web languages there are, but [Ruby on Rails](http://rubyonrails.org/) is a framework you'll have to learn too. It's not that difficult, it's pretty easy once you've done the Ruby course on Codecademy and their documentation is pretty awesome.
- PHP is the most common language used for websites that I've seen. Not extremely easy to learn, but pretty useful to nevertheless.
- Python is a good back-end manager for websites too. And it's an extremely easy language to learn, and you can do so much with Python its insane. If you buy a [Raspberry Pi](http://www.raspberrypi.org/faqs), it teaches you how to program. [Mark Ormesher](http://markormesher.co.uk), a friend of mine, built a robot car using Python, Java and a Raspberry Pi!

The good news is, once you've learned a language like PHP, Python, Ruby, JavaScript, Java, Objective-C even VB.NET, every other language becomes a tenth as difficult to learn. The difficult things to learn are the different processes of thinking and of logic used, things like conditionals or loops. For example, a conditional is a statement that depends on a truth value, like:

if (isSnowing)
    classesAreCancelled = true
else
    classesAreCancelled = false

A loop is similar, except that it's like asking keep asking "Is it snowing? Is it still snowing? Is it still snowing? Is it still snowing?" until it finds out that it's not longer snowing, so it exits the loop.

while (isSnowing)
    classesAreCancelled = true

There you go, that's two of the "difficult" things to understand in programming.

Follow me on Twitter [@FaresKAlaboud](http://twitter.com/FaresKAlaboud) and keep an eye on [KCL Tech's Facebook page](http://facebook.com/KCLTech) for more of our awesome events.


text:
using System.Collections.Generic;
using OrchardCore.Modules;
using Microsoft.Extensions.Logging;
using OrchardCore.ContentManagement.Handlers;
using OrchardCore.ContentManagement.Metadata;

namespace OrchardCore.ContentManagement.Drivers.Coordinators
{
    /// <summary>
    /// This component coordinates how parts are affecting content items.
    /// </summary>
    public class ContentPartHandlerCoordinator : ContentHandlerBase
    {
        private readonly ITypeActivatorFactory<ContentPart> _contentPartFactory;
        private readonly IEnumerable<IContentPartHandler> _partHandlers;
        private readonly IContentDefinitionManager _contentDefinitionManager;
        private readonly ITypeActivatorFactory<ContentField> _contentFieldFactory;

        public ContentPartHandlerCoordinator(
            ITypeActivatorFactory<ContentPart> contentPartFactory,
            IEnumerable<IContentPartHandler> partHandlers,
            ITypeActivatorFactory<ContentField> contentFieldFactory,
            IContentDefinitionManager contentDefinitionManager,
            ILogger<ContentPartHandlerCoordinator> logger)
        {
            _contentPartFactory = contentPartFactory;
            _contentFieldFactory = contentFieldFactory;
            _partHandlers = partHandlers;
            _contentDefinitionManager = contentDefinitionManager;

            Logger = logger;
        }

        public ILogger Logger { get; set; }

        public override void Activating(ActivatingContentContext context)
        {
            // This method is called on New()
            // Adds all the parts to a content item based on the content type definition.

            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;

                // We create the part from it's known type or from a generic one
                var part = _contentPartFactory.GetTypeActivator(partName).CreateInstance();

                _partHandlers.Invoke(handler => handler.Activating(context, part), Logger);

                context.Builder.Weld(typePartDefinition.Name, part);
            }
        }

        public override void Activated(ActivatedContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, partName) as ContentPart;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Activated(context, part), Logger);
                }
            }
        }

        public override void Creating(CreateContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);

                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Creating(context, part), Logger);
                }
            }
        }

        public override void Created(CreateContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);

                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Created(context, part), Logger);
                }
            }
        }

        public override void Initializing(InitializingContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);

                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart;
                _partHandlers.Invoke(handler => handler.Initializing(context, part), Logger);
            }
        }

        public override void Initialized(InitializingContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);

                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Initialized(context, part), Logger);
                }
            }
        }

        public override void Loading(LoadContentContext context)
        {
            // This method is called on Get()
            // Adds all the missing parts to a content item based on the content type definition.
            // A part is missing if the content type is changed and an old content item is loaded,
            // like edited.

            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
            {
                return;
            }

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var part = context.ContentItem.Get<ContentPart>(typePartDefinition.Name);

                if (part == null)
                {
                    part = _contentPartFactory.GetTypeActivator(partName).CreateInstance();
                    context.ContentItem.Weld(typePartDefinition.Name, part);
                }

                _partHandlers.Invoke(handler => handler.Loading(context, part), Logger);

                foreach (var partFieldDefinition in typePartDefinition.PartDefinition.Fields)
                {
                    var fieldName = partFieldDefinition.Name;

                    if (!part.Has(fieldName))
                    {
                        var activator = _contentFieldFactory.GetTypeActivator(partFieldDefinition.FieldDefinition.Name);
                        context.ContentItem.Get<ContentPart>(typePartDefinition.Name).Weld(fieldName, activator.CreateInstance());
                    }
                }
            }
        }

        public override void Loaded(LoadContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);

                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Loaded(context, part), Logger);
                }
            }
        }

        public override void Publishing(PublishContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Publishing(context, part), Logger);
                }
            }
        }

        public override void Published(PublishContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Published(context, part), Logger);
                }
            }
        }

        public override void Removing(RemoveContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Removing(context, part), Logger);
                }
            }
        }

        public override void Removed(RemoveContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Removed(context, part), Logger);
                }
            }
        }

        public override void Unpublishing(PublishContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Unpublishing(context, part), Logger);
                }
            }
        }

        public override void Unpublished(PublishContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Unpublished(context, part), Logger);
                }
            }
        }

        public override void Updating(UpdateContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Updating(context, part), Logger);
                }
            }
        }

        public override void Updated(UpdateContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart; ;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.Updated(context, part), Logger);
                }
            }
        }

        public override void Versioning(VersionContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);

                var buildingPart = context.BuildingContentItem.Get(activator.Type, partName) as ContentPart;
                var existingPart = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart;

                if (buildingPart != null && existingPart != null)
                {
                    _partHandlers.Invoke(handler => handler.Versioning(context, existingPart, buildingPart), Logger);
                }
            }
        }

        public override void Versioned(VersionContentContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);

                var buildingPart = (ContentPart)context.BuildingContentItem.Get(activator.Type, partName);
                var existingPart = (ContentPart)context.ContentItem.Get(activator.Type, typePartDefinition.Name);

                if (buildingPart != null && existingPart != null)
                {
                    _partHandlers.Invoke(handler => handler.Versioned(context, existingPart, buildingPart), Logger);
                }
            }
        }

        public override void GetContentItemAspect(ContentItemAspectContext context)
        {
            var contentTypeDefinition = _contentDefinitionManager.GetTypeDefinition(context.ContentItem.ContentType);
            if (contentTypeDefinition == null)
                return;

            foreach (var typePartDefinition in contentTypeDefinition.Parts)
            {
                var partName = typePartDefinition.PartDefinition.Name;
                var activator = _contentPartFactory.GetTypeActivator(partName);
                var part = context.ContentItem.Get(activator.Type, typePartDefinition.Name) as ContentPart;

                if (part != null)
                {
                    _partHandlers.Invoke(handler => handler.GetContentItemAspect(context, part), Logger);
                }
            }
        }
    }
}


text:
package tsdb_test

import (
	"fmt"
	"io/ioutil"
	"os"
	"path/filepath"
	"reflect"
	"testing"

	"github.com/influxdata/influxdb/internal"
	"github.com/influxdata/influxdb/logger"
	"github.com/influxdata/influxdb/models"
	"github.com/influxdata/influxdb/pkg/slices"
	"github.com/influxdata/influxdb/tsdb"
	"github.com/influxdata/influxdb/tsdb/index/inmem"
	"github.com/influxdata/influxdb/tsdb/index/tsi1"
	"github.com/influxdata/influxql"
)

// Ensure iterator can merge multiple iterators together.
func TestMergeSeriesIDIterators(t *testing.T) {
	itr := tsdb.MergeSeriesIDIterators(
		tsdb.NewSeriesIDSliceIterator([]uint64{1, 2, 3}),
		tsdb.NewSeriesIDSliceIterator(nil),
		tsdb.NewSeriesIDSliceIterator([]uint64{1, 2, 3, 4}),
	)

	if e, err := itr.Next(); err != nil {
		t.Fatal(err)
	} else if !reflect.DeepEqual(e, tsdb.SeriesIDElem{SeriesID: 1}) {
		t.Fatalf("unexpected elem(0): %#v", e)
	}
	if e, err := itr.Next(); err != nil {
		t.Fatal(err)
	} else if !reflect.DeepEqual(e, tsdb.SeriesIDElem{SeriesID: 2}) {
		t.Fatalf("unexpected elem(1): %#v", e)
	}
	if e, err := itr.Next(); err != nil {
		t.Fatal(err)
	} else if !reflect.DeepEqual(e, tsdb.SeriesIDElem{SeriesID: 3}) {
		t.Fatalf("unexpected elem(2): %#v", e)
	}
	if e, err := itr.Next(); err != nil {
		t.Fatal(err)
	} else if !reflect.DeepEqual(e, tsdb.SeriesIDElem{SeriesID: 4}) {
		t.Fatalf("unexpected elem(3): %#v", e)
	}
	if e, err := itr.Next(); err != nil {
		t.Fatal(err)
	} else if e.SeriesID != 0 {
		t.Fatalf("expected nil elem: %#v", e)
	}
}

func TestIndexSet_MeasurementNamesByExpr(t *testing.T) {
	// Setup indexes
	indexes := map[string]*Index{}
	for _, name := range tsdb.RegisteredIndexes() {
		idx := MustOpenNewIndex(name)
		idx.AddSeries("cpu", map[string]string{"region": "east"})
		idx.AddSeries("cpu", map[string]string{"region": "west", "secret": "foo"})
		idx.AddSeries("disk", map[string]string{"secret": "foo"})
		idx.AddSeries("mem", map[string]string{"region": "west"})
		idx.AddSeries("gpu", map[string]string{"region": "east"})
		idx.AddSeries("pci", map[string]string{"region": "east", "secret": "foo"})
		indexes[name] = idx
		defer idx.Close()
	}

	authorizer := &internal.AuthorizerMock{
		AuthorizeSeriesReadFn: func(database string, measurement []byte, tags models.Tags) bool {
			if tags.GetString("secret") != "" {
				t.Logf("Rejecting series db=%s, m=%s, tags=%v", database, measurement, tags)
				return false
			}
			return true
		},
	}

	type example struct {
		name     string
		expr     influxql.Expr
		expected [][]byte
	}

	// These examples should be run without any auth.
	examples := []example{
		{name: "all", expected: slices.StringsToBytes("cpu", "disk", "gpu", "mem", "pci")},
		{name: "EQ", expr: influxql.MustParseExpr(`region = 'west'`), expected: slices.StringsToBytes("cpu", "mem")},
		{name: "NEQ", expr: influxql.MustParseExpr(`region != 'west'`), expected: slices.StringsToBytes("gpu", "pci")},
		{name: "EQREGEX", expr: influxql.MustParseExpr(`region =~ /.*st/`), expected: slices.StringsToBytes("cpu", "gpu", "mem", "pci")},
		{name: "NEQREGEX", expr: influxql.MustParseExpr(`region !~ /.*est/`), expected: slices.StringsToBytes("gpu", "pci")},
	}

	// These examples should be run with the authorizer.
	authExamples := []example{
		{name: "all", expected: slices.StringsToBytes("cpu", "gpu", "mem")},
		{name: "EQ", expr: influxql.MustParseExpr(`region = 'west'`), expected: slices.StringsToBytes("mem")},
		{name: "NEQ", expr: influxql.MustParseExpr(`region != 'west'`), expected: slices.StringsToBytes("gpu")},
		{name: "EQREGEX", expr: influxql.MustParseExpr(`region =~ /.*st/`), expected: slices.StringsToBytes("cpu", "gpu", "mem")},
		{name: "NEQREGEX", expr: influxql.MustParseExpr(`region !~ /.*est/`), expected: slices.StringsToBytes("gpu")},
	}

	for _, idx := range tsdb.RegisteredIndexes() {
		t.Run(idx, func(t *testing.T) {
			t.Run("no authorization", func(t *testing.T) {
				for _, example := range examples {
					t.Run(example.name, func(t *testing.T) {
						names, err := indexes[idx].IndexSet().MeasurementNamesByExpr(nil, example.expr)
						if err != nil {
							t.Fatal(err)
						} else if !reflect.DeepEqual(names, example.expected) {
							t.Fatalf("got names: %v, expected %v", slices.BytesToStrings(names), slices.BytesToStrings(example.expected))
						}
					})
				}
			})

			t.Run("with authorization", func(t *testing.T) {
				for _, example := range authExamples {
					t.Run(example.name, func(t *testing.T) {
						names, err := indexes[idx].IndexSet().MeasurementNamesByExpr(authorizer, example.expr)
						if err != nil {
							t.Fatal(err)
						} else if !reflect.DeepEqual(names, example.expected) {
							t.Fatalf("got names: %v, expected %v", slices.BytesToStrings(names), slices.BytesToStrings(example.expected))
						}
					})
				}
			})
		})
	}
}

func TestIndex_Sketches(t *testing.T) {
	checkCardinalities := func(t *testing.T, index *Index, state string, series, tseries, measurements, tmeasurements int) {
		// Get sketches and check cardinality...
		sketch, tsketch, err := index.SeriesSketches()
		if err != nil {
			t.Fatal(err)
		}

		// delta calculates a rough 10% delta. If i is small then a minimum value
		// of 2 is used.
		delta := func(i int) int {
			v := i / 10
			if v == 0 {
				v = 2
			}
			return v
		}

		// series cardinality should be well within 10%.
		if got, exp := int(sketch.Count()), series; got-exp < -delta(series) || got-exp > delta(series) {
			t.Errorf("[%s] got series cardinality %d, expected ~%d", state, got, exp)
		}

		// check series tombstones
		if got, exp := int(tsketch.Count()), tseries; got-exp < -delta(tseries) || got-exp > delta(tseries) {
			t.Errorf("[%s] got series tombstone cardinality %d, expected ~%d", state, got, exp)
		}

		// Check measurement cardinality.
		if sketch, tsketch, err = index.MeasurementsSketches(); err != nil {
			t.Fatal(err)
		}

		if got, exp := int(sketch.Count()), measurements; got != exp { //got-exp < -delta(measurements) || got-exp > delta(measurements) {
			t.Errorf("[%s] got measurement cardinality %d, expected ~%d", state, got, exp)
		}

		if got, exp := int(tsketch.Count()), tmeasurements; got != exp { //got-exp < -delta(tmeasurements) || got-exp > delta(tmeasurements) {
			t.Errorf("[%s] got measurement tombstone cardinality %d, expected ~%d", state, got, exp)
		}
	}

	test := func(t *testing.T, index string) error {
		idx := MustNewIndex(index)
		if index, ok := idx.Index.(*tsi1.Index); ok {
			// Override the log file max size to force a log file compaction sooner.
			// This way, we will test the sketches are correct when they have been
			// compacted into IndexFiles, and also when they're loaded from
			// IndexFiles after a re-open.
			tsi1.WithMaximumLogFileSize(1 << 10)(index)
		}

		// Open the index
		idx.MustOpen()
		defer idx.Close()

		series := genTestSeries(10, 5, 3)
		// Add series to index.
		for _, serie := range series {
			if err := idx.AddSeries(serie.Measurement, serie.Tags.Map()); err != nil {
				t.Fatal(err)
			}
		}

		// Check cardinalities after adding series.
		checkCardinalities(t, idx, "initial", 2430, 0, 10, 0)

		// Re-open step only applies to the TSI index.
		if _, ok := idx.Index.(*tsi1.Index); ok {
			// Re-open the index.
			if err := idx.Reopen(); err != nil {
				panic(err)
			}

			// Check cardinalities after the reopen
			checkCardinalities(t, idx, "initial|reopen", 2430, 0, 10, 0)
		}

		// Drop some series
		if err := idx.DropMeasurement([]byte("measurement2")); err != nil {
			return err
		} else if err := idx.DropMeasurement([]byte("measurement5")); err != nil {
			return err
		}

		// Check cardinalities after the delete
		checkCardinalities(t, idx, "initial|reopen|delete", 2430, 486, 10, 2)

		// Re-open step only applies to the TSI index.
		if _, ok := idx.Index.(*tsi1.Index); ok {
			// Re-open the index.
			if err := idx.Reopen(); err != nil {
				panic(err)
			}

			// Check cardinalities after the reopen
			checkCardinalities(t, idx, "initial|reopen|delete|reopen", 2430, 486, 10, 2)
		}
		return nil
	}

	for _, index := range tsdb.RegisteredIndexes() {
		t.Run(index, func(t *testing.T) {
			if err := test(t, index); err != nil {
				t.Fatal(err)
			}
		})
	}
}

// Index wraps a series file and index.
type Index struct {
	tsdb.Index
	rootPath  string
	indexType string
	sfile     *tsdb.SeriesFile
}

// MustNewIndex will initialize a new index using the provide type. It creates
// everything under the same root directory so it can be cleanly removed on Close.
//
// The index will not be opened.
func MustNewIndex(index string) *Index {
	opts := tsdb.NewEngineOptions()
	opts.IndexVersion = index

	rootPath, err := ioutil.TempDir("", "influxdb-tsdb")
	fmt.Println(rootPath)
	if err != nil {
		panic(err)
	}

	seriesPath, err := ioutil.TempDir(rootPath, tsdb.SeriesFileDirectory)
	if err != nil {
		panic(err)
	}

	sfile := tsdb.NewSeriesFile(seriesPath)
	if err := sfile.Open(); err != nil {
		panic(err)
	}

	if index == inmem.IndexName {
		opts.InmemIndex = inmem.NewIndex("db0", sfile)
	}

	i, err := tsdb.NewIndex(0, "db0", filepath.Join(rootPath, "index"), tsdb.NewSeriesIDSet(), sfile, opts)
	if err != nil {
		panic(err)
	}

	if testing.Verbose() {
		i.WithLogger(logger.New(os.Stderr))
	}

	idx := &Index{
		Index:     i,
		indexType: index,
		rootPath:  rootPath,
		sfile:     sfile,
	}
	return idx
}

// MustOpenNewIndex will initialize a new index using the provide type and opens
// it.
func MustOpenNewIndex(index string) *Index {
	idx := MustNewIndex(index)
	idx.MustOpen()
	return idx
}

// MustOpen opens the underlying index or panics.
func (i *Index) MustOpen() {
	if err := i.Index.Open(); err != nil {
		panic(err)
	}
}

func (idx *Index) IndexSet() *tsdb.IndexSet {
	return &tsdb.IndexSet{Indexes: []tsdb.Index{idx.Index}, SeriesFile: idx.sfile}
}

func (idx *Index) AddSeries(name string, tags map[string]string) error {
	t := models.NewTags(tags)
	key := fmt.Sprintf("%s,%s", name, t.HashKey())
	return idx.CreateSeriesIfNotExists([]byte(key), []byte(name), t)
}

// Reopen closes and re-opens the underlying index, without removing any data.
func (i *Index) Reopen() error {
	if err := i.Index.Close(); err != nil {
		return err
	}

	if err := i.sfile.Close(); err != nil {
		return err
	}

	i.sfile = tsdb.NewSeriesFile(i.sfile.Path())
	if err := i.sfile.Open(); err != nil {
		return err
	}

	opts := tsdb.NewEngineOptions()
	opts.IndexVersion = i.indexType
	if i.indexType == inmem.IndexName {
		opts.InmemIndex = inmem.NewIndex("db0", i.sfile)
	}

	idx, err := tsdb.NewIndex(0, "db0", filepath.Join(i.rootPath, "index"), tsdb.NewSeriesIDSet(), i.sfile, opts)
	if err != nil {
		return err
	}
	i.Index = idx
	return i.Index.Open()
}

// Close closes the index cleanly and removes all on-disk data.
func (i *Index) Close() error {
	if err := i.Index.Close(); err != nil {
		return err
	}

	if err := i.sfile.Close(); err != nil {
		return err
	}
	//return os.RemoveAll(i.rootPath)
	return nil
}


text:
from collections import OrderedDict
from typing import Dict, Type

from .base import InstanceAdminTransport
from .grpc import InstanceAdminGrpcTransport
from .grpc_asyncio import InstanceAdminGrpcAsyncIOTransport

# Compile a registry of transports.
_transport_registry = OrderedDict()  # type: Dict[str, Type[InstanceAdminTransport]]
_transport_registry["grpc"] = InstanceAdminGrpcTransport
_transport_registry["grpc_asyncio"] = InstanceAdminGrpcAsyncIOTransport

__all__ = (
    "InstanceAdminTransport",
    "InstanceAdminGrpcTransport",
    "InstanceAdminGrpcAsyncIOTransport",
)


text:
class Palindrome{

    public boolean palindrome(Node head){
        Node current = head;
        Node reversehead = null;

        while(current.next != null){
            Node temp = current.next;
            current.next = reversehead;
            reversehead = current;
            current = temp;
        }

        current.next = reversehead;

        reversehead = current;

        while(head.next != null && reversehead.next != null){
            if(head.val != reversehead.val) return false;
            head = head.next;
            reversehead = reversehead.next;
        }

        if(head.next != null) return false;
        if(reversehead.next != null) return false;

        return true;
    }
}