<commit_before>package com.imcode.imcms.api;

import imcode.server.IMCServiceInterface;
import imcode.server.document.*;
import imcode.server.document.textdocument.MenuItemDomainObject;
import imcode.server.document.textdocument.TextDocumentDomainObject;
import imcode.server.user.UserAndRoleMapper;
import imcode.server.user.UserDomainObject;

import java.io.IOException;

public class DocumentService {

    private SecurityChecker securityChecker;
    private DocumentMapper documentMapper;
    private DocumentPermissionSetMapper documentPermissionSetMapper;
    private UserAndRoleMapper userAndRoleMapper;
    private IMCServiceInterface service;

    Document wrapDocumentDomainObject( DocumentDomainObject document ) {
        Document result;

        if ( document instanceof TextDocumentDomainObject ) {
            result = new TextDocument( (TextDocumentDomainObject)document, service, securityChecker, this, documentMapper,
                                       documentPermissionSetMapper, userAndRoleMapper );
        } else if ( document instanceof UrlDocumentDomainObject ) {
            result = new UrlDocument( (UrlDocumentDomainObject)document, service, securityChecker, this, documentMapper,
                                      documentPermissionSetMapper, userAndRoleMapper );
        } else {
            result = new Document( document, service, securityChecker, this, documentMapper,
                                   documentPermissionSetMapper, userAndRoleMapper );
        }
        return result;
    }

    public DocumentService( IMCServiceInterface service, SecurityChecker securityChecker, DocumentMapper documentMapper,
                            DocumentPermissionSetMapper documentPermissionSetMapper,
                            UserAndRoleMapper userAndRoleMapper ) {
        this.service = service;
        this.securityChecker = securityChecker;
        this.documentMapper = documentMapper;
        this.documentPermissionSetMapper = documentPermissionSetMapper;
        this.userAndRoleMapper = userAndRoleMapper;
    }

    /**
     * Used to get a document of any type. If you need a specific document, i.e. a TextDocument, use @see getTextDocument
     * instead.
     *
     * @param documentId The id number of the document requested, also somtimes known as "meta_id"
     * @return The document The type is usually a subclass to document, if there exist one.
     * @throws com.imcode.imcms.api.NoPermissionException
     *          If the current user dosen't have the rights to read this document.
     */
    public Document getDocument( int documentId ) throws NoPermissionException {
        DocumentDomainObject doc = documentMapper.getDocument( documentId );
        Document result = null;
        if ( null != doc ) {
            result = wrapDocumentDomainObject( doc );
            securityChecker.hasAtLeastDocumentReadPermission( result );
        }
        return result;
    }

    /**
     * @param documentId The id number of the document requested, also somtimes known as "meta_id"
     * @return The document
     * @throws com.imcode.imcms.api.NoPermissionException
     *          If the current user dosen't have the rights to read this document.
     */
    public TextDocument getTextDocument( int documentId ) throws NoPermissionException {
        Document doc = getDocument( documentId );
        return (TextDocument)doc;
    }

    /**
     * @param documentId The id number of the document requested, also somtimes known as "meta_id"
     * @return The document
     * @throws com.imcode.imcms.api.NoPermissionException
     *          If the current user dosen't have the rights to read this document.
     */
    public UrlDocument getUrlDocument( int documentId ) throws NoPermissionException {
        Document doc = getDocument( documentId );
        return (UrlDocument)doc;
    }

    public TextDocument createAndSaveNewTextDocument( Document parent ) throws NoPermissionException, MaxCategoriesOfTypeExceededException {
        DocumentDomainObject newDoc = createAndSaveNewDocument( DocumentDomainObject.DOCTYPE_TEXT, parent );
        return (TextDocument)getDocument( newDoc.getId() );
    }

    public UrlDocument createAndSaveNewUrlDocument( Document parent ) throws NoPermissionException, MaxCategoriesOfTypeExceededException {
        DocumentDomainObject newDoc = createAndSaveNewDocument( DocumentDomainObject.DOCTYPE_URL, parent );
        return (UrlDocument)getDocument( newDoc.getId() );
    }

    private DocumentDomainObject createAndSaveNewDocument( int doctype, Document parent ) throws MaxCategoriesOfTypeExceededException, NoPermissionException {
        securityChecker.hasEditPermission( parent.getId() );
        UserDomainObject user = securityChecker.getCurrentLoggedInUser();
        DocumentDomainObject newDoc = documentMapper.createDocumentOfTypeFromParent( doctype, parent.internalDocument, user );
        try {
            documentMapper.saveNewDocument( newDoc, user );
        } catch ( MaxCategoryDomainObjectsOfTypeExceededException e ) {
            throw new MaxCategoriesOfTypeExceededException( e );
        }
        return newDoc;
    }

    /**
     * @deprecated Use createNewUrlDocument( int parentId ) instead.
     */
    public UrlDocument createNewUrlDocument( int parentId, int parentMenuNumber ) throws NoPermissionException {
        Document parentDocument = getDocument( parentId );
        UrlDocument newUrlDocument = null;
        try {
            newUrlDocument = createAndSaveNewUrlDocument( parentDocument );
        } catch ( MaxCategoriesOfTypeExceededException e ) {
            throw new RuntimeException( e );
        }
        addDocumentToMenu( parentDocument, parentMenuNumber, newUrlDocument );

        return newUrlDocument;
    }

    /**
     * @deprecated Use createNewTextDocument( int parentId ) instead.
     */
    public TextDocument createNewTextDocument( int parentId, int parentMenuNumber ) throws NoPermissionException {
        Document parentDocument = getDocument( parentId );
        TextDocument newTextDocument = null;
        try {
            newTextDocument = createAndSaveNewTextDocument( parentDocument );
        } catch ( MaxCategoriesOfTypeExceededException e ) {
            throw new RuntimeException( e );
        }
        addDocumentToMenu( parentDocument, parentMenuNumber, newTextDocument );

        return newTextDocument;
    }

    private void addDocumentToMenu( Document parentDocument, int parentMenuNumber, Document document ) {
        UserDomainObject user = securityChecker.getCurrentLoggedInUser();
        DocumentDomainObject internalParentDocument = parentDocument.internalDocument;
        ( (TextDocumentDomainObject)internalParentDocument ).getMenu( parentMenuNumber ).addMenuItem( new MenuItemDomainObject( document.internalDocument ) );
        documentMapper.saveDocument( internalParentDocument, user );
    }

    public void saveChanges( Document document ) throws NoPermissionException, MaxCategoriesOfTypeExceededException {
        securityChecker.hasEditPermission( document );
        try {
            documentMapper.saveDocument( document.getInternal(), securityChecker.getCurrentLoggedInUser() );
        } catch ( MaxCategoryDomainObjectsOfTypeExceededException e ) {
            throw new MaxCategoriesOfTypeExceededException( e );
        }
    }

    public Category getCategory( CategoryType categoryType, String categoryName ) {
        // Allow everyone to get a Category. No security check.
        final CategoryDomainObject category = documentMapper.getCategory( categoryType.getInternal(), categoryName );
        if ( null != category ) {<commit_msg>Bug 2276 : Made the saveChanges( Document ) sunchronized.<commit_after>package com.imcode.imcms.api;

import imcode.server.IMCServiceInterface;
import imcode.server.document.*;
import imcode.server.document.textdocument.MenuItemDomainObject;
import imcode.server.document.textdocument.TextDocumentDomainObject;
import imcode.server.user.UserAndRoleMapper;
import imcode.server.user.UserDomainObject;

import java.io.IOException;

public class DocumentService {

    private SecurityChecker securityChecker;
    private DocumentMapper documentMapper;
    private DocumentPermissionSetMapper documentPermissionSetMapper;
    private UserAndRoleMapper userAndRoleMapper;
    private IMCServiceInterface service;

    Document wrapDocumentDomainObject( DocumentDomainObject document ) {
        Document result;

        if ( document instanceof TextDocumentDomainObject ) {
            result = new TextDocument( (TextDocumentDomainObject)document, service, securityChecker, this, documentMapper,
                                       documentPermissionSetMapper, userAndRoleMapper );
        } else if ( document instanceof UrlDocumentDomainObject ) {
            result = new UrlDocument( (UrlDocumentDomainObject)document, service, securityChecker, this, documentMapper,
                                      documentPermissionSetMapper, userAndRoleMapper );
        } else {
            result = new Document( document, service, securityChecker, this, documentMapper,
                                   documentPermissionSetMapper, userAndRoleMapper );
        }
        return result;
    }

    public DocumentService( IMCServiceInterface service, SecurityChecker securityChecker, DocumentMapper documentMapper,
                            DocumentPermissionSetMapper documentPermissionSetMapper,
                            UserAndRoleMapper userAndRoleMapper ) {
        this.service = service;
        this.securityChecker = securityChecker;
        this.documentMapper = documentMapper;
        this.documentPermissionSetMapper = documentPermissionSetMapper;
        this.userAndRoleMapper = userAndRoleMapper;
    }

    /**
     * Used to get a document of any type. If you need a specific document, i.e. a TextDocument, use @see getTextDocument
     * instead.
     *
     * @param documentId The id number of the document requested, also somtimes known as "meta_id"
     * @return The document The type is usually a subclass to document, if there exist one.
     * @throws com.imcode.imcms.api.NoPermissionException
     *          If the current user dosen't have the rights to read this document.
     */
    public Document getDocument( int documentId ) throws NoPermissionException {
        DocumentDomainObject doc = documentMapper.getDocument( documentId );
        Document result = null;
        if ( null != doc ) {
            result = wrapDocumentDomainObject( doc );
            securityChecker.hasAtLeastDocumentReadPermission( result );
        }
        return result;
    }

    /**
     * @param documentId The id number of the document requested, also somtimes known as "meta_id"
     * @return The document
     * @throws com.imcode.imcms.api.NoPermissionException
     *          If the current user dosen't have the rights to read this document.
     */
    public TextDocument getTextDocument( int documentId ) throws NoPermissionException {
        Document doc = getDocument( documentId );
        return (TextDocument)doc;
    }

    /**
     * @param documentId The id number of the document requested, also somtimes known as "meta_id"
     * @return The document
     * @throws com.imcode.imcms.api.NoPermissionException
     *          If the current user dosen't have the rights to read this document.
     */
    public UrlDocument getUrlDocument( int documentId ) throws NoPermissionException {
        Document doc = getDocument( documentId );
        return (UrlDocument)doc;
    }

    public TextDocument createAndSaveNewTextDocument( Document parent ) throws NoPermissionException, MaxCategoriesOfTypeExceededException {
        DocumentDomainObject newDoc = createAndSaveNewDocument( DocumentDomainObject.DOCTYPE_TEXT, parent );
        return (TextDocument)getDocument( newDoc.getId() );
    }

    public UrlDocument createAndSaveNewUrlDocument( Document parent ) throws NoPermissionException, MaxCategoriesOfTypeExceededException {
        DocumentDomainObject newDoc = createAndSaveNewDocument( DocumentDomainObject.DOCTYPE_URL, parent );
        return (UrlDocument)getDocument( newDoc.getId() );
    }

    private DocumentDomainObject createAndSaveNewDocument( int doctype, Document parent ) throws MaxCategoriesOfTypeExceededException, NoPermissionException {
        securityChecker.hasEditPermission( parent.getId() );
        UserDomainObject user = securityChecker.getCurrentLoggedInUser();
        DocumentDomainObject newDoc = documentMapper.createDocumentOfTypeFromParent( doctype, parent.internalDocument, user );
        try {
            documentMapper.saveNewDocument( newDoc, user );
        } catch ( MaxCategoryDomainObjectsOfTypeExceededException e ) {
            throw new MaxCategoriesOfTypeExceededException( e );
        }
        return newDoc;
    }

    /**
     * @deprecated Use createNewUrlDocument( int parentId ) instead.
     */
    public UrlDocument createNewUrlDocument( int parentId, int parentMenuNumber ) throws NoPermissionException {
        Document parentDocument = getDocument( parentId );
        UrlDocument newUrlDocument = null;
        try {
            newUrlDocument = createAndSaveNewUrlDocument( parentDocument );
        } catch ( MaxCategoriesOfTypeExceededException e ) {
            throw new RuntimeException( e );
        }
        addDocumentToMenu( parentDocument, parentMenuNumber, newUrlDocument );

        return newUrlDocument;
    }

    /**
     * @deprecated Use createNewTextDocument( int parentId ) instead.
     */
    public TextDocument createNewTextDocument( int parentId, int parentMenuNumber ) throws NoPermissionException {
        Document parentDocument = getDocument( parentId );
        TextDocument newTextDocument = null;
        try {
            newTextDocument = createAndSaveNewTextDocument( parentDocument );
        } catch ( MaxCategoriesOfTypeExceededException e ) {
            throw new RuntimeException( e );
        }
        addDocumentToMenu( parentDocument, parentMenuNumber, newTextDocument );

        return newTextDocument;
    }

    private void addDocumentToMenu( Document parentDocument, int parentMenuNumber, Document document ) {
        UserDomainObject user = securityChecker.getCurrentLoggedInUser();
        DocumentDomainObject internalParentDocument = parentDocument.internalDocument;
        ( (TextDocumentDomainObject)internalParentDocument ).getMenu( parentMenuNumber ).addMenuItem( new MenuItemDomainObject( document.internalDocument ) );
        documentMapper.saveDocument( internalParentDocument, user );
    }

    /** Saves the changes on a modified document. Warning this mehtod is synchronized, witch meens that it only handles one
     *  request at a time, no concurrent handling of multiple calls.
     * @param document
     * @throws NoPermissionException
     * @throws MaxCategoriesOfTypeExceededException
     */
    public synchronized  void saveChanges( Document document ) throws NoPermissionException, MaxCategoriesOfTypeExceededException {
        securityChecker.hasEditPermission( document );
        try {
            documentMapper.saveDocument( document.getInternal(), securityChecker.getCurrentLoggedInUser() );
        } catch ( MaxCategoryDomainObjectsOfTypeExceededException e ) {
            throw new MaxCategoriesOfTypeExceededException( e );
        }
    }

    public Category getCategory( CategoryType categoryType, String categoryName ) {
        // Allow everyone to get a Category. No security check.
        final CategoryDomainObject category = documentMapper.getCategory( categoryType.getInternal(), categoryName );
        if ( null != category ) {
{'fraction_non_alphanumeric': 0.062313598578590014, 'fraction_numerical': 0.00025382321213274954, 'mean_word_length': 3.224068614312517, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 6, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '7244461', 'n_tokens_mistral': 3688, 'n_tokens_neox': 3619, 'n_words': 1032}