001/*
002 * The contents of this file are subject to the terms of the Common Development and
003 * Distribution License (the License). You may not use this file except in compliance with the
004 * License.
005 *
006 * You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
007 * specific language governing permission and limitations under the License.
008 *
009 * When distributing Covered Software, include this CDDL Header Notice in each file and include
010 * the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
011 * Header, with the fields enclosed by brackets [] replaced by your own identifying
012 * information: "Portions Copyright [year] [name of copyright owner]".
013 *
014 * Copyright 2009 Sun Microsystems, Inc.
015 * Portions Copyright 2011-2015 ForgeRock AS.
016 */
017package org.opends.server.controls;
018
019import static org.opends.messages.ProtocolMessages.*;
020import static org.opends.server.util.ServerConstants.*;
021import static org.opends.server.util.StaticUtils.getExceptionMessage;
022
023import java.io.IOException;
024
025import org.forgerock.i18n.LocalizableMessage;
026import org.forgerock.opendj.io.ASN1;
027import org.forgerock.opendj.io.ASN1Reader;
028import org.forgerock.opendj.io.ASN1Writer;
029import org.forgerock.opendj.ldap.ByteString;
030import org.forgerock.opendj.ldap.ResultCode;
031import org.opends.server.replication.common.MultiDomainServerState;
032import org.opends.server.types.Control;
033import org.opends.server.types.DirectoryException;
034
035/** This class implements the control used to browse the external changelog. */
036public class ExternalChangelogRequestControl
037       extends Control
038{
039  private MultiDomainServerState cookie;
040
041  /** ControlDecoder implementation to decode this control from a ByteString. */
042  private static final class Decoder
043      implements ControlDecoder<ExternalChangelogRequestControl>
044  {
045    @Override
046    public ExternalChangelogRequestControl decode(boolean isCritical, ByteString value) throws DirectoryException
047    {
048      return new ExternalChangelogRequestControl(isCritical, decodeCookie(value));
049    }
050
051    private MultiDomainServerState decodeCookie(ByteString value) throws DirectoryException
052    {
053      if (value == null)
054      {
055        return new MultiDomainServerState();
056      }
057
058      ASN1Reader reader = ASN1.getReader(value);
059      String mdssValue = null;
060      try
061      {
062        mdssValue = reader.readOctetStringAsString();
063        return new MultiDomainServerState(mdssValue);
064      }
065      catch (Exception e)
066      {
067        try
068        {
069          mdssValue = value.toString();
070          return new MultiDomainServerState(mdssValue);
071        }
072        catch (Exception e2)
073        {
074          LocalizableMessage message = ERR_CANNOT_DECODE_CONTROL_VALUE.get(
075              getOID() + " x=" + value.toHexString() + " v=" + mdssValue, getExceptionMessage(e));
076          throw new DirectoryException(ResultCode.PROTOCOL_ERROR, message, e);
077        }
078      }
079    }
080
081    @Override
082    public String getOID()
083    {
084      return OID_ECL_COOKIE_EXCHANGE_CONTROL;
085    }
086  }
087
088  /** The Control Decoder that can be used to decode this control. */
089  public static final ControlDecoder<ExternalChangelogRequestControl> DECODER = new Decoder();
090
091  /**
092   * Create a new external change log request control to contain the cookie.
093   * @param isCritical Specifies whether the control is critical.
094   * @param cookie Specifies the cookie value.
095   */
096  public ExternalChangelogRequestControl(boolean isCritical, MultiDomainServerState cookie)
097  {
098    super(OID_ECL_COOKIE_EXCHANGE_CONTROL, isCritical);
099    this.cookie = cookie;
100  }
101
102  /**
103   * Returns a copy of the cookie value.
104   *
105   * @return a copy of the cookie value
106   */
107  public MultiDomainServerState getCookie()
108  {
109    return new MultiDomainServerState(cookie);
110  }
111
112  @Override
113  public void toString(StringBuilder buffer)
114  {
115    buffer.append("ExternalChangelogRequestControl(cookie=");
116    this.cookie.toString(buffer);
117    buffer.append(")");
118  }
119
120  @Override
121  protected void writeValue(ASN1Writer writer) throws IOException
122  {
123    writer.writeStartSequence(ASN1.UNIVERSAL_OCTET_STRING_TYPE);
124    writer.writeOctetString(this.cookie.toString());
125    writer.writeEndSequence();
126  }
127}