Initial Resoning for Optimizer
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/ByteArrayFragment.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/ByteArrayFragment.java
new file mode 100644
index 0000000..69ccf98
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/ByteArrayFragment.java
@@ -0,0 +1,70 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+import java.util.Arrays;
+import java.util.Objects;
+
+public class ByteArrayFragment implements Fragment {
+
+    private int id;
+    private final byte[] data;
+    private Ensemble parent;
+
+    public ByteArrayFragment(byte[] data) {
+        this.id = id;
+        this.data = data;
+    }
+
+    @Override public void setId(int id) {
+        this.id = id;
+    }
+
+    @Override public int getId() {
+        return id;
+    }
+
+    @Override public Ensemble getParent() {
+        return this.parent;
+    }
+
+    @Override public void setParent(Ensemble ensemble) {
+        this.parent = ensemble;
+    }
+
+    @Override public byte[] getBytes() {
+        return data;
+    }
+
+    @Override public boolean equals(Object o) {
+        if (this == o) return true;
+        if (o == null || getClass() != o.getClass()) return false;
+        ByteArrayFragment that = (ByteArrayFragment) o;
+        return id == that.id;
+    }
+
+    @Override public int hashCode() {
+        return Objects.hash(id);
+    }
+
+    @Override public String toString() {
+        return "#" + getId() + " = " + Arrays.toString(data);
+    }
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Ensemble.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Ensemble.java
new file mode 100644
index 0000000..a48f3c5
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Ensemble.java
@@ -0,0 +1,73 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+import java.util.ArrayDeque;
+import java.util.Deque;
+import java.util.HashSet;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Queue;
+import java.util.Set;
+import java.util.concurrent.atomic.AtomicInteger;
+
+/** Ensemble of fragments that share a stack **/
+public class Ensemble {
+
+    private final AtomicInteger fragmentCounter = new AtomicInteger(0);
+
+    private final Set<Fragment> fragments = new HashSet<>();
+    private final Deque<OptimizerOperation> operations = new LinkedList<>();
+
+    public int getFragmendId() {
+        return fragmentCounter.getAndIncrement();
+    }
+
+    public void addFragment(Fragment fragment) {
+        if (fragment.getParent() != null) {
+            throw new IllegalArgumentException("This Fragment alredy belongs to an ensemble!");
+        }
+        fragment.setId(getFragmendId());
+        fragment.setParent(this);
+        this.fragments.add(fragment);
+    }
+
+    public Set<Fragment> getFragments() {
+        return this.fragments;
+    }
+
+    public void remove(Fragment fragment) {
+        assert fragment.getParent() == this;
+        // Remove by Id
+        this.fragments.remove(fragment);
+    }
+
+    public void addOperation(OptimizerOperation operation) {
+        this.operations.addFirst(operation);
+    }
+
+    @Override public String toString() {
+        return "Ensemble{" +
+            "fragments=" + fragments +
+            ", operations=" + operations +
+            '}';
+    }
+
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Fragment.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Fragment.java
new file mode 100644
index 0000000..ba7f3be
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Fragment.java
@@ -0,0 +1,36 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+/**
+ * Elements the Optimizer works on.
+ * Fragments are data holding elements of a request.
+ */
+public interface Fragment {
+
+    /** Unique Fragment ID **/
+    int getId();
+
+    void setId(int id);
+
+    Ensemble getParent();
+
+    void setParent(Ensemble ensemble);
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/FragmentAdapter.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/FragmentAdapter.java
new file mode 100644
index 0000000..bfec7ec
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/FragmentAdapter.java
@@ -0,0 +1,43 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+public abstract class FragmentAdapter implements Fragment {
+
+    private int id;
+    private Ensemble parent;
+
+    @Override public int getId() {
+        return this.id;
+    }
+
+    @Override public void setId(int id) {
+        this.id = id;
+    }
+
+    @Override public Ensemble getParent() {
+        return this.parent;
+    }
+
+    @Override public void setParent(Ensemble ensemble) {
+        this.parent = ensemble;
+    }
+
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/MergeOperation.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/MergeOperation.java
new file mode 100644
index 0000000..f3f3a00
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/MergeOperation.java
@@ -0,0 +1,28 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+public abstract class MergeOperation implements OptimizerOperation {
+
+    public abstract boolean canMerge(Fragment f1, Fragment f2);
+
+    public abstract Fragment merge(Fragment f1, Fragment f2);
+
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Optimizer.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Optimizer.java
new file mode 100644
index 0000000..07586d1
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/Optimizer.java
@@ -0,0 +1,108 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * General Principle
+ *
+ * API
+ * S_Req = Set{Req_1{I, ..., I}, ..., Req_n{I, ..., I}}
+ * ------------------
+ * Optimizer
+ * - S_opt = Set{Req*_1{I, ..., I}, ..., Req*_m{I, ..., I}}
+ * - [O_1, ..., O_k] with O_i : Set of Response -> Set of Response
+ * - O_1 : Set{Res*_1, ..., Res*_m} with Res*_1 response to Req*_1, ...
+ * - O_k : Set{Res_1, ..., Res_n} with Res_1 response to Req_1, ...
+ * - Im(O_i) = Sup(O_i+1)
+ * - S* = Set{Res*_1, ..., Res*_m} -- O_1 --> S*_1 ---> .... -- O_k --> S = Set{Res_1, ..., Res_n}
+ * ------------------
+ * Protocol Layer (S*)
+ * ------------------
+ * Deoptimizer Layer (O, S_Res*
+ *
+ *
+ *
+ *
+ *
+ *
+ *
+ *
+ * <code>
+ *     Max Packet Size 2
+ *     Read: (0 = [1,2,3,4,5])
+ *
+ *     Operation 1 : Split
+ *      split(1, 2, -> 0) + (1 = [1, 2]), (2 = [3, 4, 5])
+ *        Operation 2: Split
+ *          merge(3, 4, -> 2) + (1 =)[1, 2]), (3 = [3, 4]), (4 = [5])
+ * </code>
+ */
+public class Optimizer<T extends Fragment> {
+
+    private static final Logger logger = LoggerFactory.getLogger(Optimizer.class);
+
+    private final List<OptimizerCondition> conditions;
+
+    public Optimizer(OptimizerCondition... conditions) {
+        this.conditions = Arrays.asList(conditions);
+    }
+
+    public Ensemble optimize(List<T> fragments) {
+        Ensemble ensemble = new Ensemble();
+        fragments.forEach(ensemble::addFragment);
+
+        logger.info("Starting optimization with Ensembke {}", ensemble);
+        // Check if all Conditions match (return directly?!)
+        boolean violation;
+        do {
+            // TODO this should also skip
+            violation = false;
+            for (OptimizerCondition condition : conditions) {
+                if (condition instanceof SingleFragmentCondition) {
+                    for (Fragment fragment : ensemble.getFragments()) {
+                        if (((SingleFragmentCondition) condition).applies(fragment)) {
+                            logger.warn("The Fragment {} violated constraint {}", fragment, condition);
+                            ((SingleFragmentCondition) condition).apply(fragment, ensemble);
+                            logger.info("Ensemble is now {}", ensemble);
+                            violation = true;
+                        }
+                    }
+                }
+            }
+        } while (violation);
+        return null;
+    }
+
+    /**
+     *  Important, the Fragments have to have identical Fragment ID!
+     */
+    public List<Fragment> deoptimize(Ensemble ensemble, List<ResponseFragment> fragments) {
+        // Check if they match with their id's
+        // Now we create a map id -> fragments to merge them in the appropriate order
+        // Operation (Set<F> -> Set<F>)
+    }
+
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/OptimizerCondition.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/OptimizerCondition.java
new file mode 100644
index 0000000..55397fa
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/OptimizerCondition.java
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+public interface OptimizerCondition {
+
+    String getName();
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/OptimizerOperation.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/OptimizerOperation.java
new file mode 100644
index 0000000..1979731
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/OptimizerOperation.java
@@ -0,0 +1,26 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+public interface OptimizerOperation {
+
+    String getName();
+
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/RequestFragment.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/RequestFragment.java
new file mode 100644
index 0000000..a276945
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/RequestFragment.java
@@ -0,0 +1,23 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+public abstract class RequestFragment extends FragmentAdapter {
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/ResponseFragment.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/ResponseFragment.java
new file mode 100644
index 0000000..a020034
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/ResponseFragment.java
@@ -0,0 +1,23 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+public abstract class ResponseFragment extends FragmentAdapter {
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/SingleFragmentCondition.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/SingleFragmentCondition.java
new file mode 100644
index 0000000..7cac7d7
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/SingleFragmentCondition.java
@@ -0,0 +1,29 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+import io.vavr.Tuple2;
+
+public interface SingleFragmentCondition extends OptimizerCondition {
+
+    boolean applies(Fragment fragment);
+
+    void apply(Fragment fragment, Ensemble ensemble);
+}
diff --git a/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/SplitOperation.java b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/SplitOperation.java
new file mode 100644
index 0000000..7d97b94
--- /dev/null
+++ b/plc4j/spi/src/main/java/org/apache/plc4x/java/spi/optimizer/SplitOperation.java
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+import io.vavr.Tuple2;
+
+public abstract class SplitOperation<T extends Fragment> implements OptimizerOperation {
+
+    public abstract boolean canSplit(T f);
+
+    public abstract Tuple2<MergeOperation, Tuple2<Fragment, Fragment>> split(T f);
+
+}
diff --git a/plc4j/spi/src/test/java/org/apache/plc4x/java/spi/optimizer/OptimizerTest.java b/plc4j/spi/src/test/java/org/apache/plc4x/java/spi/optimizer/OptimizerTest.java
new file mode 100644
index 0000000..69d45ef
--- /dev/null
+++ b/plc4j/spi/src/test/java/org/apache/plc4x/java/spi/optimizer/OptimizerTest.java
@@ -0,0 +1,105 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.plc4x.java.spi.optimizer;
+
+import org.junit.jupiter.api.Test;
+
+import java.util.Arrays;
+
+class OptimizerTest {
+
+    @Test
+    void playWithOptimizing() {
+        ByteArrayFragment fragment1 = new ByteArrayFragment(new byte[]{1, 2, 3, 4, 5});
+
+        Optimizer<ByteArrayFragment> optimizer = new Optimizer<>(new MaximalSizeCondition(2));
+
+        // Optimize the ensemble with Conditions
+        optimizer.optimize(Arrays.asList(fragment1));
+    }
+
+    private static class MaximalSizeCondition implements SingleFragmentCondition {
+
+        private final int maximalSize;
+
+        private MaximalSizeCondition(int maximalSize) {
+            this.maximalSize = maximalSize;
+        }
+
+        @Override public boolean applies(Fragment fragment) {
+            if (!(fragment instanceof ByteArrayFragment)) {
+                return false;
+            }
+            return fragment.getBytes().length > maximalSize;
+        }
+
+        @Override public void apply(Fragment fragment, Ensemble ensemble) {
+            // Split it up to two fragments with the appropriate rule
+            byte[] bytes = fragment.getBytes();
+            byte[] first = Arrays.copyOf(bytes, maximalSize);
+            byte[] second = Arrays.copyOfRange(bytes, maximalSize, bytes.length);
+            // Remove our Fragment from the Ensemble and add the two new ones
+            ensemble.remove(fragment);
+            ByteArrayFragment fragment1 = new ByteArrayFragment(first);
+            ByteArrayFragment fragment2 = new ByteArrayFragment(second);
+            ensemble.addFragment(fragment1);
+            ensemble.addFragment(fragment2);
+            // Create Inverse Rule and Register it
+            ensemble.addOperation(new MergeByteArrayFragmentsOp(fragment1.getId(), fragment2.getId(), fragment.getId()));
+        }
+
+        @Override public String toString() {
+            return "MaximumPaketSize(" + maximalSize + ")";
+        }
+
+        @Override public String getName() {
+            return "MaximumPaketSize(" + maximalSize + ")";
+        }
+
+        private static class MergeByteArrayFragmentsOp extends MergeOperation {
+
+            private final int f1;
+            private final int f2;
+            private final int targetId;
+
+            public MergeByteArrayFragmentsOp(int f1, int f2, int targetId) {
+                this.f1 = f1;
+                this.f2 = f2;
+                this.targetId = targetId;
+            }
+
+            @Override public String getName() {
+                return String.format("Merge #%d + #%d -> #%d", f1, f2, targetId);
+            }
+
+            @Override public boolean canMerge(Fragment f1, Fragment f2) {
+                return false;
+            }
+
+            @Override public Fragment merge(Fragment f1, Fragment f2) {
+                return null;
+            }
+
+            @Override public String toString() {
+                return getName();
+            }
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/site/asciidoc/developers/optimizer.adoc b/src/site/asciidoc/developers/optimizer.adoc
new file mode 100644
index 0000000..7069923
--- /dev/null
+++ b/src/site/asciidoc/developers/optimizer.adoc
@@ -0,0 +1,68 @@
+[ditaa,optimizer-architecture]
+....
++------------------------------------------------+
+|c05A                                            |
+|                      API                       |
+|                                                |
++------------------------------------------------+
+        |                                  ^
+        |                                  |
+        |                                  |
+{Req_1, ..., Req_n}<---------------->{n PLC Responses }
+        |                                  |
+        |                                  |
+        |                                  |
++----------------+                         |
+|c0FF            |                         |
+|    Optimizer   |------------------{O_1, ..., O_k}---------------+
+|                |                         |                      |
++----------------+                         |                      |
+        |                                  |                      |
+        |                                  |                      |
+{Q_1, ..., Q_m}                            |                      |
+        |                                  |                      |
+        |                                  |                      |
+        |                                  |                      |
++------------------------------------------------+                |
+|c05A   |                                        |                |
+|       v                                        |                |
+|  +----------------+                            |                |
+|  |c0FF Optimizer  |                            |                |
+|  +----------------+                            |                |
+|                                                |                |
+|  +----------------+                            |                |
+|  |c0FF Optimizer  |                            |                |
+|  +----------------+                            |                |
+|                                                |                |
++------------------------------------------------+                |
+        |                                  ^                      |
+        |                                  |                      |
+        |                                  |                      |
+        |                         {Res_1, ..., Res_n}             |
+        |                                  |                      |
+        |                                  |                      |
+        |                         +----------------+              |
+        |                         |c0FF            |              |
+  {m PLC Requests }<-----+        |  Deoptimizer   |<-------------+
+        |                |        |                |
+        |                |        +----------------+
+        |                |                 ^
+        |                |                 |
+        |                |                 |
+        |                +------->{Res_1, ..., Res_m}
+        |                                  |
+        v                                  |
++------------------------------------------------+
+|c05A                                            |
+|                    Netty                       |
+|                                                |
++------------------------------------------------+
+....
+
+
+
++----------------+                 +----------------+
+|c05A            |                 |c05A            |
+|    Optimizer   |                 |    Optimizer   |
+|                |                 |                |
++----------------+                 +----------------+
\ No newline at end of file