[infinispan-commits] Infinispan SVN: r1294 - in trunk/server/memcached/src: test/java/org/infinispan/server/memcached and 1 other directory.

infinispan-commits at lists.jboss.org infinispan-commits at lists.jboss.org
Fri Dec 11 11:47:35 EST 2009


Author: galder.zamarreno at jboss.com
Date: 2009-12-11 11:47:35 -0500 (Fri, 11 Dec 2009)
New Revision: 1294

Added:
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DecrementCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/IncrementCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/NumericCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/Reply.java
Removed:
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ErrorReply.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/StorageReply.java
Modified:
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AddCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AppendCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CasCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CommandFactory.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayed.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayedEntry.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/MemcachedTextServer.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ReplaceCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/SetCommand.java
   trunk/server/memcached/src/main/java/org/infinispan/server/memcached/TextCommandDecoder.java
   trunk/server/memcached/src/test/java/org/infinispan/server/memcached/FunctionalTest.java
Log:
[ISPN-173] (Build memcached server module) Completed delete, incr and decr commands.

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AddCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AddCommand.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AddCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -39,17 +39,17 @@
    }
 
    @Override
-   protected StorageReply put(String key, int flags, byte[] data, long expiry) {
+   protected Reply put(String key, int flags, byte[] data, long expiry) {
       Value value = new Value(flags, data);
       Object prev = cache.putIfAbsent(key, value, expiry, TimeUnit.MILLISECONDS);
       return reply(prev);
    }
 
-   private StorageReply reply(Object prev) {
+   private Reply reply(Object prev) {
       if (prev == null)
-         return StorageReply.STORED;
+         return Reply.STORED;
       else 
-         return StorageReply.NOT_STORED;
+         return Reply.NOT_STORED;
    }
 
 }

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AppendCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AppendCommand.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/AppendCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -41,7 +41,7 @@
    }
 
    @Override
-   protected StorageReply put(String key, int flags, byte[] data) {
+   protected Reply put(String key, int flags, byte[] data) {
       Value append = new Value(flags, data);
       Value current = (Value) cache.get(key);
       if (current != null) {
@@ -49,11 +49,11 @@
          Value next = new Value(current.getFlags(), concatenated);
          boolean replaced = cache.replace(key, current, next);
          if (replaced)
-            return StorageReply.STORED;
+            return Reply.STORED;
          else
-            return StorageReply.NOT_STORED;
+            return Reply.NOT_STORED;
       } else {
-         return StorageReply.NOT_STORED;
+         return Reply.NOT_STORED;
       }
    }
 
@@ -62,7 +62,7 @@
    }
 
    @Override
-   protected StorageReply put(String key, int flags, byte[] data, long expiry) {
+   protected Reply put(String key, int flags, byte[] data, long expiry) {
       return put(key, flags, data); // ignore expiry
    }
 

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CasCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CasCommand.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CasCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -46,21 +46,21 @@
    }
 
    @Override
-   protected StorageReply put(String key, int flags, byte[] data, long expiry) {
+   protected Reply put(String key, int flags, byte[] data, long expiry) {
       Value old = (Value) cache.get(key);
       if (old != null) {
          if (old.getCas() == cas) {
             Value value = new Value(flags, data);
             boolean replaced = cache.replace(key, old, value);
             if (replaced)
-               return StorageReply.STORED;
+               return Reply.STORED;
             else
-               return StorageReply.EXISTS;
+               return Reply.EXISTS;
          } else {
-            return StorageReply.EXISTS;
+            return Reply.EXISTS;
          }
       }
-      return StorageReply.NOT_FOUND;
+      return Reply.NOT_FOUND;
    }
 
    public static CasCommand newCasCommand(Cache cache, StorageParameters params, long cas, byte[] data) {

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CommandFactory.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CommandFactory.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/CommandFactory.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -24,6 +24,7 @@
 
 import java.io.EOFException;
 import java.io.IOException;
+import java.math.BigInteger;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
@@ -33,6 +34,7 @@
 import org.infinispan.Cache;
 import org.infinispan.util.logging.Log;
 import org.infinispan.util.logging.LogFactory;
+import org.jboss.util.NotImplementedException;
 
 /**
  * CommandFactory.
@@ -44,6 +46,7 @@
    private static final Log log = LogFactory.getLog(CommandFactory.class);
 
    private final Cache cache;
+   @Deprecated
    private final BlockingQueue<DeleteDelayedEntry> queue;
    
    public CommandFactory(Cache cache, BlockingQueue<DeleteDelayedEntry> queue) {
@@ -79,11 +82,16 @@
             keys.addAll(Arrays.asList(args).subList(1, args.length));
             return RetrievalCommand.newRetrievalCommand(cache, type, new RetrievalParameters(keys));
          case DELETE:
+            String delKey = getKey(args[1]);
+            return DeleteCommand.newDeleteCommand(cache, delKey, queue);
+         case INCR:
+         case DECR:
             String key = getKey(args[1]);
-            long time = getOptionalTime(args[2]);
-            return DeleteCommand.newDeleteCommand(cache, key, time, queue);
+            // Value is defined as unsigned 64-integer (or simply unsigned long in java language)
+            BigInteger value = new BigInteger(args[2]);
+            return NumericCommand.newNumericCommand(cache, type, key, value);
          default:
-            return null;
+            throw new NotImplementedException("Parsed type not implemented yet");
       }
    }
 
@@ -111,8 +119,4 @@
       return Integer.parseInt(bytes);
    }
 
-   private long getOptionalTime(String time) {
-      if (time == null) return 0;
-      return Long.parseLong(time); // seconds
-   }
 }

Added: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DecrementCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DecrementCommand.java	                        (rev 0)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DecrementCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -0,0 +1,54 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2009, Red Hat, Inc. and/or its affiliates, and
+ * individual contributors as indicated by the @author tags. See the
+ * copyright.txt file in the distribution for a full listing of
+ * individual contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.infinispan.server.memcached;
+
+import java.math.BigInteger;
+
+import org.infinispan.Cache;
+import org.infinispan.util.logging.Log;
+import org.infinispan.util.logging.LogFactory;
+
+/**
+ * DecrementCommand.
+ * 
+ * @author Galder Zamarreño
+ * @since 4.0
+ */
+public class DecrementCommand extends NumericCommand {
+   private static final Log log = LogFactory.getLog(DecrementCommand.class);
+
+   public DecrementCommand(Cache cache, CommandType type, String key, BigInteger value) {
+      super(cache, type, key, value);
+   }
+
+   @Override
+   protected BigInteger operate(BigInteger oldValue, BigInteger newValue) {
+      if (log.isTraceEnabled()) log.trace("Substract {0} to {1}", newValue, oldValue);
+      BigInteger b = oldValue.subtract(newValue);
+      if (b.signum() < 0)
+         return BigInteger.valueOf(0);
+      else
+         return b; 
+   }
+
+}

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteCommand.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -22,7 +22,11 @@
  */
 package org.infinispan.server.memcached;
 
+import static org.infinispan.server.memcached.TextProtocolUtil.CRLF;
+import static org.jboss.netty.buffer.ChannelBuffers.wrappedBuffer;
+
 import java.util.concurrent.BlockingQueue;
+import java.util.concurrent.Delayed;
 
 import org.infinispan.Cache;
 import org.jboss.netty.channel.Channel;
@@ -37,7 +41,11 @@
 
    final Cache cache;
    final String key;
+   @Deprecated
+   /** @deprecated No longer in memcached spec: http://github.com/memcached/memcached/blob/master/doc/protocol.txt */
    final long time;
+   @Deprecated
+   /** @deprecated No longer in memcached spec: http://github.com/memcached/memcached/blob/master/doc/protocol.txt */
    final BlockingQueue<DeleteDelayedEntry> queue;
 
    DeleteCommand(Cache cache, String key, long time, BlockingQueue<DeleteDelayedEntry> queue) {
@@ -54,15 +62,27 @@
 
    @Override
    public Object perform(Channel ch) throws Exception {
+      Reply reply;
       if (time > 0) {
-         queue.offer(new DeleteDelayedEntry(key, time));
+         DeleteDelayedEntry d = new DeleteDelayedEntry(key, time);
+         queue.offer(d);
+         reply = Reply.DELETED;
       } else {
-         cache.remove(key);
+         Object prev = cache.remove(key);
+         reply = reply(prev);
       }
+      ch.write(wrappedBuffer(wrappedBuffer(reply.bytes()), wrappedBuffer(CRLF)));
       return null;
    }
 
-   public static DeleteCommand newDeleteCommand(Cache cache, String key, long time, BlockingQueue<DeleteDelayedEntry> queue) {
-      return new DeleteCommand(cache, key, time, queue);
+   private Reply reply(Object prev) {
+      if (prev == null)
+         return Reply.NOT_FOUND;
+      else
+         return Reply.DELETED;
    }
+
+   public static DeleteCommand newDeleteCommand(Cache cache, String key, BlockingQueue<DeleteDelayedEntry> queue) {
+      return new DeleteCommand(cache, key, 0, queue);
+   }
 }

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayed.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayed.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayed.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -33,7 +33,9 @@
  * 
  * @author Galder Zamarreño
  * @since 4.0
+ * @deprecated No longer in memcached spec: http://github.com/memcached/memcached/blob/master/doc/protocol.txt
  */
+ at Deprecated
 public class DeleteDelayed implements Runnable {
    private static final Log log = LogFactory.getLog(DeleteDelayed.class);
 

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayedEntry.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayedEntry.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/DeleteDelayedEntry.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -30,7 +30,9 @@
  * 
  * @author Galder Zamarreño
  * @since 4.0
+ * @deprecated No longer in memcached spec: http://github.com/memcached/memcached/blob/master/doc/protocol.txt
  */
+ at Deprecated
 public class DeleteDelayedEntry implements Delayed {
 
    final String key;

Deleted: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ErrorReply.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ErrorReply.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ErrorReply.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -1,33 +0,0 @@
-/*
- * JBoss, Home of Professional Open Source.
- * Copyright 2009, Red Hat, Inc. and/or its affiliates, and
- * individual contributors as indicated by the @author tags. See the
- * copyright.txt file in the distribution for a full listing of
- * individual contributors.
- *
- * This is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Lesser General Public License as
- * published by the Free Software Foundation; either version 2.1 of
- * the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this software; if not, write to the Free
- * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
- * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
- */
-package org.infinispan.server.memcached;
-
-/**
- * ErrorReply.
- * 
- * @author Galder Zamarreño
- * @since 4.0
- */
-public enum ErrorReply {
-   ERROR, CLIENT_ERROR, SERVER_ERROR;
-}

Added: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/IncrementCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/IncrementCommand.java	                        (rev 0)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/IncrementCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -0,0 +1,50 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2009, Red Hat, Inc. and/or its affiliates, and
+ * individual contributors as indicated by the @author tags. See the
+ * copyright.txt file in the distribution for a full listing of
+ * individual contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.infinispan.server.memcached;
+
+import java.math.BigInteger;
+
+import org.infinispan.Cache;
+import org.infinispan.util.logging.Log;
+import org.infinispan.util.logging.LogFactory;
+
+/**
+ * IncrementCommand.
+ * 
+ * @author Galder Zamarreño
+ * @since 4.0
+ */
+public class IncrementCommand extends NumericCommand {
+   private static final Log log = LogFactory.getLog(IncrementCommand.class);
+
+   public IncrementCommand(Cache cache, CommandType type, String key, BigInteger value) {
+      super(cache, type, key, value);
+   }
+
+   @Override
+   protected BigInteger operate(BigInteger oldValue, BigInteger newValue) {
+      if (log.isTraceEnabled()) log.trace("Increment {0} with {1}", oldValue, newValue);
+      return oldValue.add(newValue);
+   }
+
+}

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/MemcachedTextServer.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/MemcachedTextServer.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/MemcachedTextServer.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -43,6 +43,7 @@
  */
 class MemcachedTextServer {
    final CacheManager manager;
+   @Deprecated
    final ExecutorService delayedExecutor;
    
    MemcachedTextServer(CacheManager manager) {

Added: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/NumericCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/NumericCommand.java	                        (rev 0)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/NumericCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -0,0 +1,91 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2009, Red Hat, Inc. and/or its affiliates, and
+ * individual contributors as indicated by the @author tags. See the
+ * copyright.txt file in the distribution for a full listing of
+ * individual contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.infinispan.server.memcached;
+
+import static org.infinispan.server.memcached.TextProtocolUtil.CRLF;
+import static org.jboss.netty.buffer.ChannelBuffers.wrappedBuffer;
+
+import java.io.IOException;
+import java.io.StreamCorruptedException;
+import java.math.BigInteger;
+
+import org.infinispan.Cache;
+import org.infinispan.CacheException;
+import org.infinispan.util.logging.Log;
+import org.infinispan.util.logging.LogFactory;
+import org.jboss.netty.channel.Channel;
+
+/**
+ * NumericCommand.
+ * 
+ * @author Galder Zamarreño
+ * @since 4.0
+ */
+public abstract class NumericCommand implements Command {
+   private static final Log log = LogFactory.getLog(NumericCommand.class);
+   final Cache cache;
+   private final CommandType type;
+   final String key;
+   final BigInteger value;
+
+   public NumericCommand(Cache cache, CommandType type, String key, BigInteger value) {
+      this.cache = cache;
+      this.type = type;
+      this.key = key;
+      this.value = value;
+   }
+
+   public CommandType getType() {
+      return type;
+   }
+
+   @Override
+   public Object perform(Channel ch) throws Exception {
+      Value old = (Value) cache.get(key);
+      if (old != null) {
+         BigInteger oldBigInt = old.getData().length == 0 ? BigInteger.valueOf(0) : new BigInteger(old.getData());
+         BigInteger newBigInt = operate(oldBigInt, value);
+         byte[] newData = newBigInt.toByteArray();
+         Value curr = new Value(old.getFlags(), newData);
+         boolean replaced = cache.replace(key, old, curr);
+         if (replaced) {
+            ch.write(wrappedBuffer(wrappedBuffer(newBigInt.toString().getBytes()), wrappedBuffer(CRLF)));
+         } else {
+            throw new CacheException("Value modified since we retrieved from the cache, old value was " + oldBigInt);
+         }
+      } else {
+         ch.write(wrappedBuffer(wrappedBuffer(Reply.NOT_FOUND.bytes()), wrappedBuffer(CRLF)));
+      }
+      return null;
+   }
+
+   protected abstract BigInteger operate(BigInteger oldValue, BigInteger newValue);
+
+   public static Command newNumericCommand(Cache cache, CommandType type, String key, BigInteger value) throws IOException {
+      switch(type) {
+         case INCR: return new IncrementCommand(cache, type, key, value);
+         case DECR: return new DecrementCommand(cache, type, key, value);
+         default: throw new StreamCorruptedException("Unable to build storage command for type: " + type);
+      }
+   }
+}

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ReplaceCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ReplaceCommand.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/ReplaceCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -39,17 +39,17 @@
    }
 
    @Override
-   protected StorageReply put(String key, int flags, byte[] data, long expiry) {
+   protected Reply put(String key, int flags, byte[] data, long expiry) {
       Value value = new Value(flags, data);
       Object prev = cache.replace(params.key, value, expiry, TimeUnit.MILLISECONDS);
       return reply(prev);
    }
 
-   private StorageReply reply(Object prev) {
+   private Reply reply(Object prev) {
       if (prev == null)
-         return StorageReply.NOT_STORED;
+         return Reply.NOT_STORED;
       else
-         return StorageReply.STORED;
+         return Reply.STORED;
    }
 
 }

Copied: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/Reply.java (from rev 1280, trunk/server/memcached/src/main/java/org/infinispan/server/memcached/StorageReply.java)
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/Reply.java	                        (rev 0)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/Reply.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -0,0 +1,38 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2009, Red Hat, Inc. and/or its affiliates, and
+ * individual contributors as indicated by the @author tags. See the
+ * copyright.txt file in the distribution for a full listing of
+ * individual contributors.
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.infinispan.server.memcached;
+
+/**
+ * StorageReply.
+ * 
+ * @author Galder Zamarreño
+ * @since 4.0
+ */
+public enum Reply {
+   STORED, NOT_STORED, EXISTS, NOT_FOUND, DELETED,
+   ERROR, CLIENT_ERROR, SERVER_ERROR;
+   
+   public byte[] bytes() {
+      return this.toString().getBytes();
+   }
+}

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/SetCommand.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/SetCommand.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/SetCommand.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -41,7 +41,6 @@
  * @since 4.0
  */
 public class SetCommand extends StorageCommand {
-
    private static final Log log = LogFactory.getLog(SetCommand.class);
 
    SetCommand(Cache cache, CommandType type, StorageParameters params, byte[] data) {
@@ -50,7 +49,7 @@
 
    @Override
    public Object perform(Channel ch) throws Exception {
-      StorageReply reply;
+      Reply reply;
       try {
          if (params.expiry == 0) {
             reply = put(params.key, params.flags, data);
@@ -77,23 +76,23 @@
          
       } catch (Exception e) {
          log.error("Unexpected exception performing command", e);
-         reply = StorageReply.NOT_STORED;
+         reply = Reply.NOT_STORED;
       }
-      ch.write(wrappedBuffer(wrappedBuffer(reply.toString().getBytes()), wrappedBuffer(CRLF)));
+      ch.write(wrappedBuffer(wrappedBuffer(reply.bytes()), wrappedBuffer(CRLF)));
       return null;
    }
 
-   protected StorageReply put(String key, int flags, byte[] data) {
+   protected Reply put(String key, int flags, byte[] data) {
       return put(key, flags, data, -1);
    }
 
-   protected StorageReply put(String key, int flags, byte[] data, long expiry) {
+   protected Reply put(String key, int flags, byte[] data, long expiry) {
       Value value = new Value(flags, data);
       cache.put(key, value, expiry, TimeUnit.MILLISECONDS);
       return reply();
    }
 
-   private StorageReply reply() {
-      return StorageReply.STORED;
+   private Reply reply() {
+      return Reply.STORED;
    }
 }

Deleted: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/StorageReply.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/StorageReply.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/StorageReply.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -1,35 +0,0 @@
-/*
- * JBoss, Home of Professional Open Source.
- * Copyright 2009, Red Hat, Inc. and/or its affiliates, and
- * individual contributors as indicated by the @author tags. See the
- * copyright.txt file in the distribution for a full listing of
- * individual contributors.
- *
- * This is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Lesser General Public License as
- * published by the Free Software Foundation; either version 2.1 of
- * the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this software; if not, write to the Free
- * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
- * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
- */
-package org.infinispan.server.memcached;
-
-/**
- * StorageReply.
- * 
- * @author Galder Zamarreño
- * @since 4.0
- */
-public enum StorageReply {
-   STORED, NOT_STORED, 
-   EXISTS, NOT_FOUND // replies only valid for cas
-   ;
-}

Modified: trunk/server/memcached/src/main/java/org/infinispan/server/memcached/TextCommandDecoder.java
===================================================================
--- trunk/server/memcached/src/main/java/org/infinispan/server/memcached/TextCommandDecoder.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/main/java/org/infinispan/server/memcached/TextCommandDecoder.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -111,14 +111,14 @@
       log.error("Unexpected exception", t);
       Channel ch = ctx.getChannel();
       if (t instanceof UnknownCommandException) {
-         ch.write(wrappedBuffer(wrappedBuffer(ErrorReply.ERROR.toString().getBytes()), wrappedBuffer(CRLF)));
+         ch.write(wrappedBuffer(wrappedBuffer(Reply.ERROR.bytes()), wrappedBuffer(CRLF)));
       } else if (t instanceof IOException) {
          StringBuilder sb = new StringBuilder();
-         sb.append(ErrorReply.CLIENT_ERROR).append(' ').append(t);
+         sb.append(Reply.CLIENT_ERROR).append(' ').append(t);
          ch.write(wrappedBuffer(wrappedBuffer(sb.toString().getBytes()), wrappedBuffer(CRLF)));
       } else {
          StringBuilder sb = new StringBuilder();
-         sb.append(ErrorReply.SERVER_ERROR).append(' ').append(t);
+         sb.append(Reply.SERVER_ERROR).append(' ').append(t);
          ch.write(wrappedBuffer(wrappedBuffer(sb.toString().getBytes()), wrappedBuffer(CRLF)));
       }
    }

Modified: trunk/server/memcached/src/test/java/org/infinispan/server/memcached/FunctionalTest.java
===================================================================
--- trunk/server/memcached/src/test/java/org/infinispan/server/memcached/FunctionalTest.java	2009-12-11 16:24:48 UTC (rev 1293)
+++ trunk/server/memcached/src/test/java/org/infinispan/server/memcached/FunctionalTest.java	2009-12-11 16:47:35 UTC (rev 1294)
@@ -61,8 +61,8 @@
       DefaultConnectionFactory d = new DefaultConnectionFactory() {
          @Override
          public long getOperationTimeout() {
-            // return 360000;
-            return 5000;
+            return 360000;
+            // return 5000;
          }
       };
       
@@ -75,7 +75,7 @@
       server.stop();
    }
    
-   public void testBasicSet(Method m) throws Exception {
+   public void testSetBasic(Method m) throws Exception {
       Future<Boolean> f = client.set(k(m), 0, v(m));
       assert f.get(5, TimeUnit.SECONDS);
       assert v(m).equals(client.get(k(m)));
@@ -110,7 +110,7 @@
       assert ret.get(k(m, "k3-")).equals(v(m, "v3-"));
    }
 
-   public void testBasicAdd(Method m) throws Exception {
+   public void testAddBasic(Method m) throws Exception {
       Future<Boolean> f = client.add(k(m), 0, v(m));
       assert f.get(5, TimeUnit.SECONDS);
       assert v(m).equals(client.get(k(m)));
@@ -149,7 +149,7 @@
       assert client.get(k(m)).equals(v(m));
    }
 
-   public void testBasicReplace(Method m) throws Exception {
+   public void testReplaceBasic(Method m) throws Exception {
       Future<Boolean> f = client.add(k(m), 0, v(m));
       assert(f.get(5, TimeUnit.SECONDS));
       assert v(m).equals(client.get(k(m)));
@@ -190,7 +190,7 @@
       assert null == client.get(k(m));
    }
 
-   public void testBasicAppend(Method m) throws Exception {
+   public void testAppendBasic(Method m) throws Exception {
       Future<Boolean> f = client.add(k(m), 0, v(m));
       assert f.get(5, TimeUnit.SECONDS);
       assert v(m).equals(client.get(k(m)));
@@ -201,7 +201,7 @@
       assert expected.equals(client.get(k(m)));
    }
 
-   public void testBasicPrepend(Method m) throws Exception {
+   public void testPrependBasic(Method m) throws Exception {
       Future<Boolean> f = client.add(k(m), 0, v(m));
       assert f.get(5, TimeUnit.SECONDS);
       assert v(m).equals(client.get(k(m)));
@@ -212,7 +212,7 @@
       assert expected.equals(client.get(k(m)));
    }
 
-   public void testBasicGets(Method m) throws Exception {
+   public void testGetsBasic(Method m) throws Exception {
       Future<Boolean> f = client.set(k(m), 0, v(m));
       assert f.get(5, TimeUnit.SECONDS);
       CASValue<Object> value = client.gets(k(m));
@@ -220,7 +220,7 @@
       assert value.getCas() != 0;
    }
 
-   public void testBasicCas(Method m) throws Exception {
+   public void testCasBasic(Method m) throws Exception {
       Future<Boolean> f = client.set(k(m), 0, v(m));
       assert f.get(5, TimeUnit.SECONDS);
       CASValue<Object> value = client.gets(k(m));
@@ -263,11 +263,74 @@
       assert CASResponse.OK == resp;
    }
 
-   public void testBasicDelete(Method m) throws Exception {
+   public void testDeleteBasic(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, v(m));
+      assert f.get(5, TimeUnit.SECONDS);
+      f = client.delete(k(m));
+      assert f.get(5, TimeUnit.SECONDS);
+   }
+
+   public void testDeleteDoesNotExist(Method m) throws Exception {
       Future<Boolean> f = client.delete(k(m));
+      assert !f.get(5, TimeUnit.SECONDS);
+   }
+
+   public void testIncrementBasic(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, 1);
       assert f.get(5, TimeUnit.SECONDS);
+      assert 2 == client.incr(k(m), 1);
    }
 
+   public void testIncrementTriple(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, 1);
+      assert f.get(5, TimeUnit.SECONDS);
+      assert 2 == client.incr(k(m), 1);
+      assert 4 == client.incr(k(m), 2);
+      assert 8 == client.incr(k(m), 4);
+   }
+
+   public void testIncrementNotExist(Method m) throws Exception {
+      assert -1 == client.incr(k(m), 1);
+   }
+
+   public void testIncrementIntegerMax(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, 0);
+      assert f.get(5, TimeUnit.SECONDS);
+      assert Integer.MAX_VALUE == client.incr(k(m), Integer.MAX_VALUE);
+   }
+
+   public void testIncrementBeyondIntegerMax(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, 1);
+      assert f.get(5, TimeUnit.SECONDS);
+      long newValue = client.incr(k(m), Integer.MAX_VALUE);
+      assert new Long(Integer.MAX_VALUE) + 1 == newValue : "New value not expected: " + newValue;
+   }
+
+   public void testDecrementBasic(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, 1);
+      assert f.get(5, TimeUnit.SECONDS);
+      assert 0 == client.decr(k(m), 1);
+   }
+
+   public void testDecrementTriple(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, 8);
+      assert f.get(5, TimeUnit.SECONDS);
+      assert 7 == client.decr(k(m), 1);
+      assert 5 == client.decr(k(m), 2);
+      assert 1 == client.decr(k(m), 4);
+   }
+
+   public void testDecrementNotExist(Method m) throws Exception {
+      assert -1 == client.decr(k(m), 1);
+   }
+
+   public void testDecrementBelowZero(Method m) throws Exception {
+      Future<Boolean> f = client.set(k(m), 0, 1);
+      assert f.get(5, TimeUnit.SECONDS);
+      long newValue = client.decr(k(m), 2);
+      assert 0 ==  newValue : "Unexpected result: " + newValue;
+   }
+
    private String k(Method method, String prefix) {
       return prefix + method.getName();
    }



More information about the infinispan-commits mailing list