contract InvestorToken is HashFutureToken{

    string internal privilege;
    string internal contractIntroduction;

    constructor() HashFutureToken("HashFuture InvestorToken", "HFIT") public
    {
        privilege = "1.Free service: Token holders enjoy free service of asset tokenization on HashFuture platform; 2.Preemptive right: Token holders have the preemptive right of buying HashFuture digital asset, namely, the priority to buy asset compare to normal users; 3.Transaction fee discount: Token holders enjoy 50% discount on transaction fee on HashFuture platform;";
        contractIntroduction = "1. This token cannot be transferred, only investor himself or herself can hold the token and enjoy the privileges; 2. The privileges of this token will be upgraded with deeper cooperation with investors and the development of HashFuture;3. If the investor quits from the HashFuture platform, this token and its privileges will be destroyed as well;";
    }

    struct IdentityInfo {
        string hashID;
        string name;
        string country;
        string photoUrl;
        string institute;
        string occupation;
        string suggestions;
    }

    mapping(uint256 => IdentityInfo) IdentityInfoOfId;

     /**
      * @param _hashID token holder customized field, the HashFuture account ID
      * @param _name token holder customized field, the name of the holder
      * @param _country token holder customized field.
      * @param _photoUrl token holder customized field, link to holder's photo
      * @param _institute token holder customized field, institute the holder works for
      * @param _occupation token holder customized field, holder's occupation in the institute he/she works in
      * @param _suggestions token holder customized field, holder's suggestions for HashFuture
      **/
    function issueToken(
        address _to,
        string _hashID,
        string _name,
        string _country,
        string _photoUrl,
        string _institute,
        string _occupation,
        string _suggestions
    )
        public onlyOwner
    {
        uint256 _tokenId = allTokens.length;

        IdentityInfoOfId[_tokenId] = IdentityInfo(
            _hashID, _name, _country, _photoUrl,
            _institute, _occupation, _suggestions
        );

        _mint(_to, _tokenId);
    }

    /**
     * @dev the contract owner can burn (recycle) any token in circulation.
     **/
    function burnToken(uint256 _tokenId) public onlyOwner{
        address tokenOwner = ownerOf(_tokenId);
        require(tokenOwner != address(0));

        delete IdentityInfoOfId[_tokenId];
        _burn(tokenOwner, _tokenId);
    }

    /**
     * @dev Get the holder's info of a token.
     * @param _tokenId id of interested token
     **/
    function getTokenInfo(uint256 _tokenId)
        external view
        returns (string, string, string, string, string, string, string)
    {
        address tokenOwner = ownerOf(_tokenId);
        require(tokenOwner != address(0));

        IdentityInfo storage pInfo = IdentityInfoOfId[_tokenId];
        return (
            pInfo.hashID,
            pInfo.name,
            pInfo.country,
            pInfo.photoUrl,
            pInfo.institute,
            pInfo.occupation,
            pInfo.suggestions
        );
    }

    /**
     * @dev Set holder's IdentityInfo of a token
     * @param _tokenId id of target token.
     * @param _name token holder customized field, the name of the holder
     * @param _country token holder customized field.
     * @param _photoUrl token holder customized field, link to holder's photo
     * @param _institute token holder customized field, institute the holder works for
     * @param _occupation token holder customized field, holder's occupation in the institute he/she works in
     * @param _suggestions token holder customized field, holder's suggestions for HashFuture
     **/
    function setIdentityInfo(
        uint256 _tokenId,
        string _name,
        string _country,
        string _photoUrl,
        string _institute,
        string _occupation,
        string _suggestions
    )
        public
        onlyOwnerOf(_tokenId)
    {
        IdentityInfo storage pInfo = IdentityInfoOfId[_tokenId];

        pInfo.name = _name;
        pInfo.country = _country;
        pInfo.photoUrl = _photoUrl;
        pInfo.institute = _institute;
        pInfo.occupation = _occupation;
        pInfo.suggestions = _suggestions;
    }

    /**
     * @dev Set suggestions for Hashfuture
     * only holder of a token can use this function
     */
    function setSuggestion(
        uint256 _tokenId,
        string _suggestions
    )
        public
        onlyOwnerOf(_tokenId)
    {
        IdentityInfoOfId[_tokenId].suggestions = _suggestions;
    }

    /**
     * @dev Get privilege of the token
     **/
    function getPrivilege() external view returns (string) {
        return privilege;
    }

    /**
     * @dev Get the introduction of the token
     **/
    function getContractIntroduction() external view returns (string) {
        return contractIntroduction;
    }

    /**
     * @dev Update token holder's privileges
     * only official operator can use this function
     **/
    function updatePrivilege(string _privilege) public onlyOwner {
        privilege = _privilege;
    }
}
/**
 * Official token issued by HashFuture Inc.
 * This is the token for inverstors and close partners.
 */
function burnToken(uint256 _tokenId) public onlyOwner{
    address tokenOwner = ownerOf(_tokenId);
    require(tokenOwner != address(0));

    delete IdentityInfoOfId[_tokenId];
    _burn(tokenOwner, _tokenId);
}

/**
 * @dev the contract owner can burn (recycle) any token in circulation.
 **/