@After
  public void shutdown() throws Exception {

    fixture.flushAndClearHibernateSession();
    fixture.flushIndexTransaction();
    System.out.println("Shutting down everything");

    Thread.sleep(1000);
  }
  @Before
  public void setUp() {

    factory = fixture.getFactory();

    // setup needed common data for each test
    fixture.initSystemData();

    fixture.save(
        factory.createContentHandler(
            "Custom content", ContentHandlerName.CUSTOM.getHandlerClassShortName()));

    MockHttpServletRequest httpRequest = new MockHttpServletRequest("GET", "/");
    ServletRequestAccessor.setRequest(httpRequest);

    dataSourceService = new DataSourceServiceImpl();
    dataSourceService.setContentService(contentService);
    dataSourceService.setTimeService(new MockTimeService(new DateTime(2010, 7, 1, 12, 0, 0, 0)));
    dataSourceService.setUserDao(userDao);

    fixture.createAndStoreNormalUserWithUserGroup("content-creator", "Creator", "testuserstore");
    fixture.createAndStoreNormalUserWithUserGroup("content-querier", "Querier", "testuserstore");

    // setup content type
    ContentTypeConfigBuilder ctyconf = new ContentTypeConfigBuilder("MyContent", "title");
    ctyconf.startBlock("MyContent");
    ctyconf.addInput("title", "text", "contentdata/title", "Title", true);
    ctyconf.addRelatedContentInput(
        "myRelatedContent", "contentdata/myRelatedContent", "My related content", false, true);
    ctyconf.endBlock();
    Document configAsXmlBytes = XMLDocumentFactory.create(ctyconf.toString()).getAsJDOMDocument();

    fixture.save(
        factory.createContentType(
            "MyRelatedType",
            ContentHandlerName.CUSTOM.getHandlerClassShortName(),
            configAsXmlBytes));
    fixture.save(factory.createUnit("MyUnit", "en"));
    fixture.save(
        factory.createCategory(
            "MyCategory",
            null,
            "MyRelatedType",
            "MyUnit",
            User.ANONYMOUS_UID,
            User.ANONYMOUS_UID,
            false));
    fixture.save(
        factory.createCategory(
            "MyOtherCategory",
            null,
            "MyRelatedType",
            "MyUnit",
            User.ANONYMOUS_UID,
            User.ANONYMOUS_UID,
            false));

    fixture.save(
        factory.createCategoryAccessForUser(
            "MyCategory", "content-creator", "read, create, approve, admin_browse"));
    fixture.save(
        factory.createCategoryAccessForUser("MyCategory", "content-querier", "read, admin_browse"));
    fixture.save(
        factory.createCategoryAccessForUser(
            "MyOtherCategory", "content-creator", "read, create, approve, admin_browse"));
    fixture.save(
        factory.createCategoryAccessForUser(
            "MyOtherCategory", "content-querier", "read, admin_browse"));

    fixture.flushAndClearHibernateSession();
    fixture.flushIndexTransaction();
  }
  @Test
  public void
      content_queried_with_both_related_child_and_parent_having_related_content_existing_as_the_queried_content_is_still_listed_as_related_content() {
    // setup: create same content in two different categories
    ContentKey grandChildContentKey =
        contentService.createContent(
            createCreateContentCommand(
                "MyCategory", createMyRelatedContentData("Grand child"), "content-creator"));

    ContentKey sonContentKey =
        contentService.createContent(
            createCreateContentCommand(
                "MyCategory",
                createMyRelatedContentData("Son", grandChildContentKey),
                "content-creator"));

    ContentKey daughterContentKey =
        contentService.createContent(
            createCreateContentCommand(
                "MyCategory", createMyRelatedContentData("Daughter"), "content-creator"));

    ContentKey fatherContentKey =
        contentService.createContent(
            createCreateContentCommand(
                "MyCategory",
                createMyRelatedContentData("Father", sonContentKey, daughterContentKey),
                "content-creator"));

    fixture.flushIndexTransaction();

    // setup: verify that the content was created
    assertEquals(4, fixture.countAllContent());

    // exercise
    DataSourceContext context = new DataSourceContext();
    context.setUser(fixture.findUserByName("content-querier"));

    String query = "categorykey = " + fixture.findCategoryByName("MyCategory").getKey();
    String orderyBy = "@key desc";
    int index = 0;
    int count = 10;
    boolean includeData = true;
    int childrenLevel = 10;
    int parentLevel = 10;

    XMLDocument xmlDocResult =
        dataSourceService.getContentByQuery(
            context, query, orderyBy, index, count, includeData, childrenLevel, parentLevel, null);

    // verify
    Document jdomDocResult = xmlDocResult.getAsJDOMDocument();

    AssertTool.assertSingleXPathValueEquals("/contents/@totalcount", jdomDocResult, "4");
    AssertTool.assertXPathEquals(
        "/contents/content/@key",
        jdomDocResult,
        fatherContentKey.toString(),
        daughterContentKey.toString(),
        sonContentKey.toString(),
        grandChildContentKey.toString());

    AssertTool.assertXPathEquals(
        "/contents/content[title = 'Father']/relatedcontentkeys/relatedcontentkey [@level = 1]/@key",
        jdomDocResult,
        sonContentKey.toString(),
        daughterContentKey.toString());

    AssertTool.assertXPathEquals(
        "/contents/content[title = 'Daughter']/relatedcontentkeys/relatedcontentkey[@level = -1]/@key",
        jdomDocResult,
        fatherContentKey.toString());
    AssertTool.assertXPathEquals(
        "/contents/content[title = 'Son']/relatedcontentkeys/relatedcontentkey[@level = -1]/@key",
        jdomDocResult,
        fatherContentKey.toString());
    AssertTool.assertXPathEquals(
        "/contents/content[title = 'Son']/relatedcontentkeys/relatedcontentkey[@level = 1]/@key",
        jdomDocResult,
        grandChildContentKey.toString());
    AssertTool.assertXPathEquals(
        "/contents/content[title = 'Grand child']/relatedcontentkeys/relatedcontentkey[@level = -1]/@key",
        jdomDocResult,
        sonContentKey.toString());
    AssertTool.assertSingleXPathValueEquals("/contents/relatedcontents/@count", jdomDocResult, "4");
    AssertTool.assertXPathEquals(
        "/contents/relatedcontents/content/@key",
        jdomDocResult,
        grandChildContentKey.toString(),
        sonContentKey.toString(),
        daughterContentKey.toString(),
        fatherContentKey.toString());
  }
  @Test
  public void
      common_content_related_to_between_two_content_is_listed_both_contents_relatedcontentkeys() {
    // setup: create same content in two different categories
    ContentKey commonChildContentKey =
        contentService.createContent(
            createCreateContentCommand(
                "MyCategory", createMyRelatedContentData("Common child"), "content-creator"));

    ContentKey contentA =
        contentService.createContent(
            createCreateContentCommand(
                "MyCategory",
                createMyRelatedContentData("Content A", commonChildContentKey),
                "content-creator"));

    ContentKey contentB =
        contentService.createContent(
            createCreateContentCommand(
                "MyCategory",
                createMyRelatedContentData("Content B", commonChildContentKey),
                "content-creator"));

    fixture.flushIndexTransaction();

    // setup: verify that 2 content is created
    assertEquals(3, fixture.countAllContent());

    // exercise
    DataSourceContext context = new DataSourceContext();
    context.setUser(fixture.findUserByName("content-querier"));

    String query = "title STARTS WITH 'Content '";
    String orderBy = "@title asc";
    int index = 0;
    int count = 10;
    boolean includeData = true;
    int childrenLevel = 1;
    int parentLevel = 0;

    XMLDocument xmlDocResult =
        dataSourceService.getContentByQuery(
            context, query, orderBy, index, count, includeData, childrenLevel, parentLevel, null);

    // verify
    Document jdomDocResult = xmlDocResult.getAsJDOMDocument();

    System.out.println(JDOMUtil.prettyPrintDocument(jdomDocResult));

    AssertTool.assertSingleXPathValueEquals("/contents/@totalcount", jdomDocResult, "2");
    AssertTool.assertXPathEquals(
        "/contents/content/@key", jdomDocResult, contentA.toString(), contentB.toString());
    AssertTool.assertXPathEquals(
        "/contents/content[ title = 'Content A']/relatedcontentkeys/relatedcontentkey/@key",
        jdomDocResult,
        commonChildContentKey.toString());
    AssertTool.assertXPathEquals(
        "/contents/content[ title = 'Content B']/relatedcontentkeys/relatedcontentkey/@key",
        jdomDocResult,
        commonChildContentKey.toString());
    AssertTool.assertSingleXPathValueEquals("/contents/relatedcontents/@count", jdomDocResult, "1");
    AssertTool.assertSingleXPathValueEquals(
        "/contents/relatedcontents/content/@key", jdomDocResult, commonChildContentKey.toString());
  }