diff --git a/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionCompiler.java b/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionCompiler.java
new file mode 100644
index 0000000..9fbedb9
--- /dev/null
+++ b/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionCompiler.java
@@ -0,0 +1,433 @@
+/*
+ * Copyright 2016-present Open Networking Laboratory
+ *
+ * Licensed 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.onosproject.net.intent.impl.compiler;
+
+import com.google.common.collect.SetMultimap;
+import org.onlab.packet.Ip4Address;
+import org.onlab.packet.IpPrefix;
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.Link;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.flow.DefaultTrafficSelector;
+import org.onosproject.net.flow.DefaultTrafficTreatment;
+import org.onosproject.net.flow.TrafficSelector;
+import org.onosproject.net.flow.TrafficTreatment;
+import org.onosproject.net.flow.instructions.L0ModificationInstruction;
+import org.onosproject.net.flow.instructions.L1ModificationInstruction;
+import org.onosproject.net.flow.instructions.L2ModificationInstruction;
+import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModEtherInstruction;
+import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModMplsBosInstruction;
+import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModMplsLabelInstruction;
+import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModTunnelIdInstruction;
+import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanIdInstruction;
+import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanPcpInstruction;
+import org.onosproject.net.flow.instructions.L3ModificationInstruction;
+import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModArpEthInstruction;
+import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModArpIPInstruction;
+import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModArpOpInstruction;
+import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModIPInstruction;
+import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModIPv6FlowLabelInstruction;
+import org.onosproject.net.flow.instructions.L4ModificationInstruction;
+import org.onosproject.net.flow.instructions.L4ModificationInstruction.ModTransportPortInstruction;
+import org.onosproject.net.intent.IntentCompilationException;
+import org.onosproject.net.intent.LinkCollectionIntent;
+
+import java.util.List;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+/**
+ * Shared APIs and implementations for Link Collection compilers.
+ */
+public class LinkCollectionCompiler<T> {
+
+    /**
+     * Helper class to encapsulate treatment and selector.
+     */
+    protected class ForwardingInstructions {
+
+        private TrafficTreatment trafficTreatment;
+
+        private TrafficSelector trafficSelector;
+
+        public ForwardingInstructions(TrafficTreatment treatment, TrafficSelector selector) {
+
+            this.trafficTreatment = treatment;
+            this.trafficSelector = selector;
+
+        }
+
+        public TrafficTreatment treatment() {
+            return this.trafficTreatment;
+        }
+
+        public TrafficSelector selector() {
+            return this.trafficSelector;
+        }
+
+    }
+
+    /**
+     * Helper method to compute input and ouput ports.
+     *
+     * @param intent the related intents
+     * @param inputPorts the input ports to compute
+     * @param outputPorts the output ports to compute
+     */
+    protected void computePorts(LinkCollectionIntent intent,
+                                SetMultimap<DeviceId, PortNumber> inputPorts,
+                                SetMultimap<DeviceId, PortNumber> outputPorts) {
+
+        for (Link link : intent.links()) {
+            inputPorts.put(link.dst().deviceId(), link.dst().port());
+            outputPorts.put(link.src().deviceId(), link.src().port());
+        }
+
+        for (ConnectPoint ingressPoint : intent.ingressPoints()) {
+            inputPorts.put(ingressPoint.deviceId(), ingressPoint.port());
+        }
+
+        for (ConnectPoint egressPoint : intent.egressPoints()) {
+            outputPorts.put(egressPoint.deviceId(), egressPoint.port());
+        }
+
+    }
+
+    /**
+     * Helper method to compute ingress and egress ports.
+     *
+     * @param intent the related intents
+     * @param ingressPorts the ingress ports to compute
+     * @param egressPorts the egress ports to compute
+     */
+    protected void computePorts(LinkCollectionIntent intent,
+                                DeviceId deviceId,
+                                Set<PortNumber> ingressPorts,
+                                Set<PortNumber> egressPorts) {
+
+        if (!intent.applyTreatmentOnEgress()) {
+            ingressPorts.addAll(intent.ingressPoints().stream()
+                    .filter(point -> point.deviceId().equals(deviceId))
+                    .map(ConnectPoint::port)
+                    .collect(Collectors.toSet()));
+        } else {
+            egressPorts.addAll(intent.egressPoints().stream()
+                    .filter(point -> point.deviceId().equals(deviceId))
+                    .map(ConnectPoint::port)
+                    .collect(Collectors.toSet()));
+        }
+
+    }
+
+    /**
+     * Creates the flows representations.
+     *
+     * @param intent the intent to compile
+     * @param deviceId the affected device
+     * @param inPorts the input ports
+     * @param outPorts the output ports
+     * @return the list of flows representations
+     */
+    protected List<T> createRules(LinkCollectionIntent intent, DeviceId deviceId,
+                                       Set<PortNumber> inPorts, Set<PortNumber> outPorts) {
+        return null;
+    }
+
+
+    /**
+     * Computes treatment and selector which will be used
+     * in the flow representation (Rule, Objective).
+     *
+     * @param intent the intent to compile
+     * @param inPort the input port
+     * @param outPorts the output ports
+     * @param ingressPorts the ingress ports
+     * @param egressPorts the egress ports
+     * @return the forwarding instruction object which encapsulates treatment and selector
+     */
+    protected ForwardingInstructions createForwardingInstructions(LinkCollectionIntent intent, PortNumber inPort,
+                                                                  Set<PortNumber> outPorts,
+                                                                  Set<PortNumber> ingressPorts,
+                                                                  Set<PortNumber> egressPorts) {
+
+        TrafficTreatment.Builder defaultTreatmentBuilder = DefaultTrafficTreatment.builder();
+        outPorts.forEach(defaultTreatmentBuilder::setOutput);
+        TrafficTreatment outputOnlyTreatment = defaultTreatmentBuilder.build();
+        TrafficSelector.Builder selectorBuilder;
+        TrafficTreatment treatment;
+        TrafficTreatment intentTreatment;
+
+        if (!intent.applyTreatmentOnEgress()) {
+            TrafficTreatment.Builder ingressTreatmentBuilder = DefaultTrafficTreatment.builder(intent.treatment());
+            outPorts.forEach(ingressTreatmentBuilder::setOutput);
+            intentTreatment = ingressTreatmentBuilder.build();
+
+            if (ingressPorts.contains(inPort)) {
+                selectorBuilder = DefaultTrafficSelector.builder(intent.selector());
+                treatment = intentTreatment;
+            } else {
+                selectorBuilder = this.createSelectorFromFwdInstructions(
+                        new ForwardingInstructions(intentTreatment, intent.selector())
+                );
+                treatment = outputOnlyTreatment;
+            }
+        } else {
+            if (outPorts.stream().allMatch(egressPorts::contains)) {
+                TrafficTreatment.Builder egressTreatmentBuilder =
+                        DefaultTrafficTreatment.builder(intent.treatment());
+                outPorts.forEach(egressTreatmentBuilder::setOutput);
+
+                selectorBuilder = DefaultTrafficSelector.builder(intent.selector());
+                treatment = egressTreatmentBuilder.build();
+            } else {
+                selectorBuilder = DefaultTrafficSelector.builder(intent.selector());
+                treatment = outputOnlyTreatment;
+            }
+        }
+
+        TrafficSelector selector = selectorBuilder.matchInPort(inPort).build();
+
+        return new ForwardingInstructions(treatment, selector);
+
+    }
+
+    /**
+     * Update the selector builder using a L0 instruction.
+     *
+     * @param builder the builder to update
+     * @param l0instruction the l0 instruction to use
+     */
+    private void updateBuilder(TrafficSelector.Builder builder, L0ModificationInstruction l0instruction) {
+        throw new IntentCompilationException("L0 not supported");
+    }
+
+    /**
+     * Update the selector builder using a L1 instruction.
+     *
+     * @param builder the builder to update
+     * @param l1instruction the l1 instruction to use
+     */
+    private void updateBuilder(TrafficSelector.Builder builder, L1ModificationInstruction l1instruction) {
+        throw new IntentCompilationException("L1 not supported");
+    }
+
+    /**
+     * Update the selector builder using a L2 instruction.
+     *
+     * @param builder the builder to update
+     * @param l2instruction the l2 instruction to use
+     */
+    private void updateBuilder(TrafficSelector.Builder builder, L2ModificationInstruction l2instruction) {
+        switch (l2instruction.subtype()) {
+            case ETH_SRC:
+            case ETH_DST:
+                ModEtherInstruction ethInstr = (ModEtherInstruction) l2instruction;
+                switch (ethInstr.subtype()) {
+                    case ETH_SRC:
+                        builder.matchEthSrc(ethInstr.mac());
+                        break;
+                    case ETH_DST:
+                        builder.matchEthDst(ethInstr.mac());
+                        break;
+                    default:
+                        throw new IntentCompilationException("Bad eth subtype");
+                }
+                break;
+            case VLAN_ID:
+                ModVlanIdInstruction vlanIdInstr = (ModVlanIdInstruction) l2instruction;
+                builder.matchVlanId(vlanIdInstr.vlanId());
+                break;
+            case VLAN_PUSH:
+                //FIXME
+                break;
+            case VLAN_POP:
+                //TODO how do we handle dropped label? remove the selector?
+                throw new IntentCompilationException("Can't handle pop label");
+            case VLAN_PCP:
+                ModVlanPcpInstruction vlanPcpInstruction = (ModVlanPcpInstruction) l2instruction;
+                builder.matchVlanPcp(vlanPcpInstruction.vlanPcp());
+                break;
+            case MPLS_LABEL:
+            case MPLS_PUSH:
+                //FIXME
+                ModMplsLabelInstruction mplsInstr = (ModMplsLabelInstruction) l2instruction;
+                builder.matchMplsLabel(mplsInstr.label());
+                break;
+            case MPLS_POP:
+                //TODO how do we handle dropped label? remove the selector?
+                throw new IntentCompilationException("Can't handle pop label");
+            case DEC_MPLS_TTL:
+                // no-op
+                break;
+            case MPLS_BOS:
+                ModMplsBosInstruction mplsBosInstr = (ModMplsBosInstruction) l2instruction;
+                builder.matchMplsBos(mplsBosInstr.mplsBos());
+                break;
+            case TUNNEL_ID:
+                ModTunnelIdInstruction tunInstr = (ModTunnelIdInstruction) l2instruction;
+                builder.matchTunnelId(tunInstr.tunnelId());
+                break;
+            default:
+                throw new IntentCompilationException("Unknown L2 Modification instruction");
+        }
+
+    }
+
+    /**
+     * Update the selector builder using a L3 instruction.
+     *
+     * @param builder the builder to update
+     * @param l3instruction the l3 instruction to use
+     */
+    private void updateBuilder(TrafficSelector.Builder builder, L3ModificationInstruction l3instruction) {
+        // TODO check ethernet proto
+        switch (l3instruction.subtype()) {
+            case IPV4_SRC:
+            case IPV4_DST:
+            case IPV6_SRC:
+            case IPV6_DST:
+                ModIPInstruction ipInstr = (ModIPInstruction) l3instruction;
+                // TODO check if ip falls in original prefix
+                IpPrefix prefix = ipInstr.ip().toIpPrefix();
+                switch (ipInstr.subtype()) {
+                    case IPV4_SRC:
+                        builder.matchIPSrc(prefix);
+                        break;
+                    case IPV4_DST:
+                        builder.matchIPSrc(prefix);
+                        break;
+                    case IPV6_SRC:
+                        builder.matchIPv6Src(prefix);
+                        break;
+                    case IPV6_DST:
+                        builder.matchIPv6Dst(prefix);
+                        break;
+                    default:
+                        throw new IntentCompilationException("Bad type for IP instruction");
+                }
+                break;
+            case IPV6_FLABEL:
+                ModIPv6FlowLabelInstruction ipFlowInstr = (ModIPv6FlowLabelInstruction) l3instruction;
+                builder.matchIPv6FlowLabel(ipFlowInstr.flowLabel());
+                break;
+            case DEC_TTL:
+                // no-op
+                break;
+            case TTL_OUT:
+                // no-op
+                break;
+            case TTL_IN:
+                // no-op
+                break;
+            case ARP_SPA:
+                ModArpIPInstruction arpIpInstr = (ModArpIPInstruction) l3instruction;
+                if (arpIpInstr.ip().isIp4()) {
+                    builder.matchArpSpa((Ip4Address) arpIpInstr.ip());
+                } else {
+                    throw new IntentCompilationException("IPv6 not supported for ARP");
+                }
+                break;
+            case ARP_SHA:
+                ModArpEthInstruction arpEthInstr = (ModArpEthInstruction) l3instruction;
+                builder.matchArpSha(arpEthInstr.mac());
+                break;
+            case ARP_OP:
+                ModArpOpInstruction arpOpInstr = (ModArpOpInstruction) l3instruction;
+                //FIXME is the long to int cast safe?
+                builder.matchArpOp((int) arpOpInstr.op());
+                break;
+            default:
+                throw new IntentCompilationException("Unknown L3 Modification instruction");
+        }
+    }
+
+    /**
+     * Update the selector builder using a L4 instruction.
+     *
+     * @param builder the builder to update
+     * @param l4instruction the l4 instruction to use
+     */
+    private void updateBuilder(TrafficSelector.Builder builder, L4ModificationInstruction l4instruction) {
+        if (l4instruction instanceof ModTransportPortInstruction) {
+            // TODO check IP proto
+            ModTransportPortInstruction l4mod = (ModTransportPortInstruction) l4instruction;
+            switch (l4mod.subtype()) {
+                case TCP_SRC:
+                    builder.matchTcpSrc(l4mod.port());
+                    break;
+                case TCP_DST:
+                    builder.matchTcpDst(l4mod.port());
+                    break;
+                case UDP_SRC:
+                    builder.matchUdpSrc(l4mod.port());
+                    break;
+                case UDP_DST:
+                    builder.matchUdpDst(l4mod.port());
+                    break;
+                default:
+                    throw new IntentCompilationException("Unknown L4 Modification instruction");
+            }
+        } else {
+            throw new IntentCompilationException("Unknown L4 Modification instruction");
+        }
+    }
+
+    /**
+     * Computes the new traffic selector using the
+     * forwarding instructions.
+     *
+     * @param fwInstructions it encapsulates the instructions to compute the new selector
+     * @return the traffic selector builder
+     */
+    private TrafficSelector.Builder createSelectorFromFwdInstructions(ForwardingInstructions fwInstructions) {
+            TrafficSelector.Builder defaultSelectorBuilder = DefaultTrafficSelector.builder(fwInstructions.selector());
+            fwInstructions.treatment().allInstructions().forEach(instruction -> {
+                switch (instruction.type()) {
+                    case L0MODIFICATION:
+                        updateBuilder(defaultSelectorBuilder, (L0ModificationInstruction) instruction);
+                        break;
+                    case L1MODIFICATION:
+                        updateBuilder(defaultSelectorBuilder, (L1ModificationInstruction) instruction);
+                        break;
+                    case L2MODIFICATION:
+                        updateBuilder(defaultSelectorBuilder, (L2ModificationInstruction) instruction);
+                        break;
+                    case L3MODIFICATION:
+                        updateBuilder(defaultSelectorBuilder, (L3ModificationInstruction) instruction);
+                        break;
+                    case L4MODIFICATION:
+                        updateBuilder(defaultSelectorBuilder, (L4ModificationInstruction) instruction);
+                        break;
+                    case NOACTION:
+                    case OUTPUT:
+                    case GROUP:
+                    case QUEUE:
+                    case TABLE:
+                    case METER:
+                    case METADATA:
+                    case EXTENSION: // TODO is extension no-op or unsupported?
+                        // Nothing to do
+                        break;
+                    default:
+                        throw new IntentCompilationException("Unknown instruction type");
+                }
+            });
+            return defaultSelectorBuilder;
+    }
+
+}
diff --git a/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentCompiler.java b/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentCompiler.java
index 53c4287..7c2157c 100644
--- a/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentCompiler.java
+++ b/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentCompiler.java
@@ -16,43 +16,22 @@
 package org.onosproject.net.intent.impl.compiler;
 
 import com.google.common.collect.HashMultimap;
+import com.google.common.collect.ImmutableSet;
 import com.google.common.collect.SetMultimap;
+import com.google.common.collect.Sets;
 import org.apache.felix.scr.annotations.Activate;
 import org.apache.felix.scr.annotations.Component;
 import org.apache.felix.scr.annotations.Deactivate;
 import org.apache.felix.scr.annotations.Reference;
 import org.apache.felix.scr.annotations.ReferenceCardinality;
-import org.onlab.packet.Ip4Address;
-import org.onlab.packet.IpPrefix;
 import org.onosproject.core.ApplicationId;
 import org.onosproject.core.CoreService;
-import org.onosproject.net.ConnectPoint;
 import org.onosproject.net.DeviceId;
-import org.onosproject.net.Link;
 import org.onosproject.net.PortNumber;
 import org.onosproject.net.flow.DefaultFlowRule;
-import org.onosproject.net.flow.DefaultTrafficSelector;
-import org.onosproject.net.flow.DefaultTrafficTreatment;
 import org.onosproject.net.flow.FlowRule;
-import org.onosproject.net.flow.TrafficSelector;
-import org.onosproject.net.flow.TrafficTreatment;
-import org.onosproject.net.flow.instructions.L2ModificationInstruction;
-import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModEtherInstruction;
-import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModMplsBosInstruction;
-import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModMplsLabelInstruction;
-import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModTunnelIdInstruction;
-import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanIdInstruction;
-import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanPcpInstruction;
-import org.onosproject.net.flow.instructions.L3ModificationInstruction;
-import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModArpEthInstruction;
-import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModArpIPInstruction;
-import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModArpOpInstruction;
-import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModIPInstruction;
-import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModIPv6FlowLabelInstruction;
-import org.onosproject.net.flow.instructions.L4ModificationInstruction.ModTransportPortInstruction;
 import org.onosproject.net.intent.FlowRuleIntent;
 import org.onosproject.net.intent.Intent;
-import org.onosproject.net.intent.IntentCompilationException;
 import org.onosproject.net.intent.IntentCompiler;
 import org.onosproject.net.intent.LinkCollectionIntent;
 
@@ -60,10 +39,14 @@
 import java.util.Collections;
 import java.util.List;
 import java.util.Set;
-import java.util.stream.Collectors;
 
+/**
+ * Compiler to produce flow rules from link collections.
+ */
 @Component(immediate = true)
-public class LinkCollectionIntentCompiler implements IntentCompiler<LinkCollectionIntent> {
+public class LinkCollectionIntentCompiler
+        extends LinkCollectionCompiler<FlowRule>
+        implements IntentCompiler<LinkCollectionIntent> {
 
     @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
     protected IntentConfigurableRegistrator registrator;
@@ -86,21 +69,11 @@
 
     @Override
     public List<Intent> compile(LinkCollectionIntent intent, List<Intent> installable) {
+
         SetMultimap<DeviceId, PortNumber> inputPorts = HashMultimap.create();
         SetMultimap<DeviceId, PortNumber> outputPorts = HashMultimap.create();
 
-        for (Link link : intent.links()) {
-            inputPorts.put(link.dst().deviceId(), link.dst().port());
-            outputPorts.put(link.src().deviceId(), link.src().port());
-        }
-
-        for (ConnectPoint ingressPoint : intent.ingressPoints()) {
-            inputPorts.put(ingressPoint.deviceId(), ingressPoint.port());
-        }
-
-        for (ConnectPoint egressPoint : intent.egressPoints()) {
-            outputPorts.put(egressPoint.deviceId(), egressPoint.port());
-        }
+        computePorts(intent, inputPorts, outputPorts);
 
         List<FlowRule> rules = new ArrayList<>();
         for (DeviceId deviceId: outputPorts.keys()) {
@@ -109,235 +82,37 @@
         return Collections.singletonList(new FlowRuleIntent(appId, rules, intent.resources()));
     }
 
-    private List<FlowRule> createRules(LinkCollectionIntent intent, DeviceId deviceId,
+    @Override
+    protected List<FlowRule> createRules(LinkCollectionIntent intent, DeviceId deviceId,
                                        Set<PortNumber> inPorts, Set<PortNumber> outPorts) {
-        TrafficTreatment.Builder defaultTreatmentBuilder = DefaultTrafficTreatment.builder();
-        outPorts.forEach(defaultTreatmentBuilder::setOutput);
-        TrafficTreatment outputOnlyTreatment = defaultTreatmentBuilder.build();
-        Set<PortNumber> ingressPorts = Collections.emptySet();
-        Set<PortNumber> egressPorts = Collections.emptySet();
 
-        if (!intent.applyTreatmentOnEgress()) {
-            ingressPorts = intent.ingressPoints().stream()
-                    .filter(point -> point.deviceId().equals(deviceId))
-                    .map(ConnectPoint::port)
-                    .collect(Collectors.toSet());
-        } else {
-            egressPorts = intent.egressPoints().stream()
-                    .filter(point -> point.deviceId().equals(deviceId))
-                    .map(ConnectPoint::port)
-                    .collect(Collectors.toSet());
-        }
+        Set<PortNumber> ingressPorts = Sets.newHashSet();
+        Set<PortNumber> egressPorts = Sets.newHashSet();
+
+        computePorts(intent, deviceId, ingressPorts, egressPorts);
 
         List<FlowRule> rules = new ArrayList<>(inPorts.size());
-        for (PortNumber inPort: inPorts) {
-            TrafficSelector.Builder selectorBuilder;
-            TrafficTreatment treatment;
-            TrafficTreatment intentTreatment;
+        Set<PortNumber> copyIngressPorts = ImmutableSet.copyOf(ingressPorts);
+        Set<PortNumber> copyEgressPorts = ImmutableSet.copyOf(egressPorts);
 
-            if (!intent.applyTreatmentOnEgress()) {
-                TrafficTreatment.Builder ingressTreatmentBuilder = DefaultTrafficTreatment.builder(intent.treatment());
-                outPorts.forEach(ingressTreatmentBuilder::setOutput);
-                intentTreatment = ingressTreatmentBuilder.build();
-
-                if (ingressPorts.contains(inPort)) {
-                    selectorBuilder = DefaultTrafficSelector.builder(intent.selector());
-                    treatment = intentTreatment;
-                } else {
-                    selectorBuilder = applyTreatmentToSelector(intent.selector(), intentTreatment);
-                    treatment = outputOnlyTreatment;
-                }
-            } else {
-                if (outPorts.stream().allMatch(egressPorts::contains)) {
-                    TrafficTreatment.Builder egressTreatmentBuilder =
-                            DefaultTrafficTreatment.builder(intent.treatment());
-                    outPorts.forEach(egressTreatmentBuilder::setOutput);
-
-                    selectorBuilder = DefaultTrafficSelector.builder(intent.selector());
-                    treatment = egressTreatmentBuilder.build();
-                } else {
-                    selectorBuilder = DefaultTrafficSelector.builder(intent.selector());
-                    treatment = outputOnlyTreatment;
-                }
+        inPorts.forEach(inport -> {
+                ForwardingInstructions instructions = this.createForwardingInstructions(intent,
+                                                                                        inport,
+                                                                                        outPorts,
+                                                                                        copyIngressPorts,
+                                                                                        copyEgressPorts);
+                FlowRule rule = DefaultFlowRule.builder()
+                        .forDevice(deviceId)
+                        .withSelector(instructions.selector())
+                        .withTreatment(instructions.treatment())
+                        .withPriority(intent.priority())
+                        .fromApp(appId)
+                        .makePermanent()
+                        .build();
+                rules.add(rule);
             }
-            TrafficSelector selector = selectorBuilder.matchInPort(inPort).build();
-
-            FlowRule rule = DefaultFlowRule.builder()
-                    .forDevice(deviceId)
-                    .withSelector(selector)
-                    .withTreatment(treatment)
-                    .withPriority(intent.priority())
-                    .fromApp(appId)
-                    .makePermanent()
-                    .build();
-            rules.add(rule);
-        }
+        );
 
         return rules;
     }
-
-    private TrafficSelector.Builder applyTreatmentToSelector(TrafficSelector selector, TrafficTreatment treatment) {
-        TrafficSelector.Builder defaultSelectorBuilder = DefaultTrafficSelector.builder(selector);
-        treatment.allInstructions().forEach(instruction -> {
-            switch (instruction.type()) {
-                case L0MODIFICATION:
-                case L1MODIFICATION:
-                    throw new IntentCompilationException("L0 and L1 mods not supported");
-                case L2MODIFICATION:
-                    L2ModificationInstruction l2mod = (L2ModificationInstruction) instruction;
-                    switch (l2mod.subtype()) {
-                        case ETH_SRC:
-                        case ETH_DST:
-                            ModEtherInstruction ethInstr = (ModEtherInstruction) l2mod;
-                            switch (ethInstr.subtype()) {
-                                case ETH_SRC:
-                                    defaultSelectorBuilder.matchEthSrc(ethInstr.mac());
-                                    break;
-                                case ETH_DST:
-                                    defaultSelectorBuilder.matchEthDst(ethInstr.mac());
-                                    break;
-                                default:
-                                    throw new IntentCompilationException("Bad eth subtype");
-                            }
-                            break;
-                        case VLAN_ID:
-                            ModVlanIdInstruction vlanIdInstr = (ModVlanIdInstruction) l2mod;
-                            defaultSelectorBuilder.matchVlanId(vlanIdInstr.vlanId());
-                            break;
-                        case VLAN_PUSH:
-                            //FIXME
-                            break;
-                        case VLAN_POP:
-                            //TODO how do we handle dropped label? remove the selector?
-                            throw new IntentCompilationException("Can't handle pop label");
-                        case VLAN_PCP:
-                            ModVlanPcpInstruction vlanPcpInstruction = (ModVlanPcpInstruction) l2mod;
-                            defaultSelectorBuilder.matchVlanPcp(vlanPcpInstruction.vlanPcp());
-                            break;
-                        case MPLS_LABEL:
-                        case MPLS_PUSH:
-                            //FIXME
-                            ModMplsLabelInstruction mplsInstr = (ModMplsLabelInstruction) l2mod;
-                            defaultSelectorBuilder.matchMplsLabel(mplsInstr.label());
-                            break;
-                        case MPLS_POP:
-                            //TODO how do we handle dropped label? remove the selector?
-                            throw new IntentCompilationException("Can't handle pop label");
-                        case DEC_MPLS_TTL:
-                            // no-op
-                            break;
-                        case MPLS_BOS:
-                            ModMplsBosInstruction mplsBosInstr = (ModMplsBosInstruction) l2mod;
-                            defaultSelectorBuilder.matchMplsBos(mplsBosInstr.mplsBos());
-                            break;
-                        case TUNNEL_ID:
-                            ModTunnelIdInstruction tunInstr = (ModTunnelIdInstruction) l2mod;
-                            defaultSelectorBuilder.matchTunnelId(tunInstr.tunnelId());
-                            break;
-                        default:
-                            throw new IntentCompilationException("Unknown L2 Modification instruction");
-                    }
-                    break;
-                case L3MODIFICATION:
-                    L3ModificationInstruction l3mod = (L3ModificationInstruction) instruction;
-                    // TODO check ethernet proto
-                    switch (l3mod.subtype()) {
-                        case IPV4_SRC:
-                        case IPV4_DST:
-                        case IPV6_SRC:
-                        case IPV6_DST:
-                            ModIPInstruction ipInstr = (ModIPInstruction) l3mod;
-                            // TODO check if ip falls in original prefix
-                            IpPrefix prefix = ipInstr.ip().toIpPrefix();
-                            switch (ipInstr.subtype()) {
-                                case IPV4_SRC:
-                                    defaultSelectorBuilder.matchIPSrc(prefix);
-                                    break;
-                                case IPV4_DST:
-                                    defaultSelectorBuilder.matchIPSrc(prefix);
-                                    break;
-                                case IPV6_SRC:
-                                    defaultSelectorBuilder.matchIPv6Src(prefix);
-                                    break;
-                                case IPV6_DST:
-                                    defaultSelectorBuilder.matchIPv6Dst(prefix);
-                                    break;
-                                default:
-                                    throw new IntentCompilationException("Bad type for IP instruction");
-                            }
-                            break;
-                        case IPV6_FLABEL:
-                            ModIPv6FlowLabelInstruction ipFlowInstr = (ModIPv6FlowLabelInstruction) l3mod;
-                            defaultSelectorBuilder.matchIPv6FlowLabel(ipFlowInstr.flowLabel());
-                            break;
-                        case DEC_TTL:
-                            // no-op
-                            break;
-                        case TTL_OUT:
-                            // no-op
-                            break;
-                        case TTL_IN:
-                            // no-op
-                            break;
-                        case ARP_SPA:
-                            ModArpIPInstruction arpIpInstr = (ModArpIPInstruction) l3mod;
-                            if (arpIpInstr.ip().isIp4()) {
-                                defaultSelectorBuilder.matchArpSpa((Ip4Address) arpIpInstr.ip());
-                            } else {
-                                throw new IntentCompilationException("IPv6 not supported for ARP");
-                            }
-                            break;
-                        case ARP_SHA:
-                            ModArpEthInstruction arpEthInstr = (ModArpEthInstruction) l3mod;
-                            defaultSelectorBuilder.matchArpSha(arpEthInstr.mac());
-                            break;
-                        case ARP_OP:
-                            ModArpOpInstruction arpOpInstr = (ModArpOpInstruction) l3mod;
-                            //FIXME is the long to int cast safe?
-                            defaultSelectorBuilder.matchArpOp((int) arpOpInstr.op());
-                            break;
-                        default:
-                            throw new IntentCompilationException("Unknown L3 Modification instruction");
-                    }
-                    break;
-                case L4MODIFICATION:
-                    if (instruction instanceof ModTransportPortInstruction) {
-                        // TODO check IP proto
-                        ModTransportPortInstruction l4mod = (ModTransportPortInstruction) instruction;
-                        switch (l4mod.subtype()) {
-                            case TCP_SRC:
-                                defaultSelectorBuilder.matchTcpSrc(l4mod.port());
-                                break;
-                            case TCP_DST:
-                                defaultSelectorBuilder.matchTcpDst(l4mod.port());
-                                break;
-                            case UDP_SRC:
-                                defaultSelectorBuilder.matchUdpSrc(l4mod.port());
-                                break;
-                            case UDP_DST:
-                                defaultSelectorBuilder.matchUdpDst(l4mod.port());
-                                break;
-                            default:
-                                throw new IntentCompilationException("Unknown L4 Modification instruction");
-                        }
-                    } else {
-                        throw new IntentCompilationException("Unknown L4 Modification instruction");
-                    }
-                    break;
-                case NOACTION:
-                case OUTPUT:
-                case GROUP:
-                case QUEUE:
-                case TABLE:
-                case METER:
-                case METADATA:
-                case EXTENSION: // TODO is extension no-op or unsupported?
-                    // Nothing to do
-                    break;
-                default:
-                    throw new IntentCompilationException("Unknown instruction type");
-            }
-        });
-        return defaultSelectorBuilder;
-    }
 }
diff --git a/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentFlowObjectivesCompiler.java b/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentFlowObjectiveCompiler.java
similarity index 67%
rename from core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentFlowObjectivesCompiler.java
rename to core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentFlowObjectiveCompiler.java
index 09c7037a..7ffff6b 100644
--- a/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentFlowObjectivesCompiler.java
+++ b/core/net/src/main/java/org/onosproject/net/intent/impl/compiler/LinkCollectionIntentFlowObjectiveCompiler.java
@@ -16,7 +16,9 @@
 package org.onosproject.net.intent.impl.compiler;
 
 import com.google.common.collect.HashMultimap;
+import com.google.common.collect.ImmutableSet;
 import com.google.common.collect.SetMultimap;
+import com.google.common.collect.Sets;
 import org.apache.felix.scr.annotations.Activate;
 import org.apache.felix.scr.annotations.Component;
 import org.apache.felix.scr.annotations.Deactivate;
@@ -24,14 +26,8 @@
 import org.apache.felix.scr.annotations.ReferenceCardinality;
 import org.onosproject.core.ApplicationId;
 import org.onosproject.core.CoreService;
-import org.onosproject.net.ConnectPoint;
 import org.onosproject.net.DeviceId;
-import org.onosproject.net.Link;
 import org.onosproject.net.PortNumber;
-import org.onosproject.net.flow.DefaultTrafficSelector;
-import org.onosproject.net.flow.DefaultTrafficTreatment;
-import org.onosproject.net.flow.TrafficSelector;
-import org.onosproject.net.flow.TrafficTreatment;
 import org.onosproject.net.flowobjective.DefaultForwardingObjective;
 import org.onosproject.net.flowobjective.DefaultNextObjective;
 import org.onosproject.net.flowobjective.FlowObjectiveService;
@@ -47,13 +43,14 @@
 import java.util.Collections;
 import java.util.List;
 import java.util.Set;
-import java.util.stream.Collectors;
 
 /**
  * Compiler to produce flow objectives from link collections.
  */
 @Component(immediate = true)
-public class LinkCollectionIntentFlowObjectivesCompiler implements IntentCompiler<LinkCollectionIntent> {
+public class LinkCollectionIntentFlowObjectiveCompiler
+        extends LinkCollectionCompiler<Objective>
+        implements IntentCompiler<LinkCollectionIntent> {
 
     @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
     protected IntentConfigurableRegistrator registrator;
@@ -79,21 +76,11 @@
 
     @Override
     public List<Intent> compile(LinkCollectionIntent intent, List<Intent> installable) {
+
         SetMultimap<DeviceId, PortNumber> inputPorts = HashMultimap.create();
         SetMultimap<DeviceId, PortNumber> outputPorts = HashMultimap.create();
 
-        for (Link link : intent.links()) {
-            inputPorts.put(link.dst().deviceId(), link.dst().port());
-            outputPorts.put(link.src().deviceId(), link.src().port());
-        }
-
-        for (ConnectPoint ingressPoint : intent.ingressPoints()) {
-            inputPorts.put(ingressPoint.deviceId(), ingressPoint.port());
-        }
-
-        for (ConnectPoint egressPoint : intent.egressPoints()) {
-            outputPorts.put(egressPoint.deviceId(), egressPoint.port());
-        }
+        computePorts(intent, inputPorts, outputPorts);
 
         List<Objective> objectives = new ArrayList<>();
         List<DeviceId> devices = new ArrayList<>();
@@ -112,49 +99,46 @@
                 new FlowObjectiveIntent(appId, devices, objectives, intent.resources()));
     }
 
-    private List<Objective> createRules(LinkCollectionIntent intent, DeviceId deviceId,
+    @Override
+    protected List<Objective> createRules(LinkCollectionIntent intent, DeviceId deviceId,
                                        Set<PortNumber> inPorts, Set<PortNumber> outPorts) {
-        Set<PortNumber> ingressPorts = intent.ingressPoints().stream()
-                .filter(point -> point.deviceId().equals(deviceId))
-                .map(ConnectPoint::port)
-                .collect(Collectors.toSet());
 
-        TrafficTreatment.Builder defaultTreatmentBuilder = DefaultTrafficTreatment.builder();
-        outPorts.forEach(defaultTreatmentBuilder::setOutput);
-        TrafficTreatment defaultTreatment = defaultTreatmentBuilder.build();
+        Set<PortNumber> ingressPorts = Sets.newHashSet();
+        Set<PortNumber> egressPorts = Sets.newHashSet();
 
-        TrafficTreatment.Builder ingressTreatmentBuilder = DefaultTrafficTreatment.builder(intent.treatment());
-        outPorts.forEach(ingressTreatmentBuilder::setOutput);
-        TrafficTreatment ingressTreatment = ingressTreatmentBuilder.build();
+        computePorts(intent, deviceId, ingressPorts, egressPorts);
 
         List<Objective> objectives = new ArrayList<>(inPorts.size());
-        for (PortNumber inPort: inPorts) {
-            TrafficSelector selector = DefaultTrafficSelector.builder(intent.selector()).matchInPort(inPort).build();
-            TrafficTreatment treatment;
-            if (ingressPorts.contains(inPort)) {
-                treatment = ingressTreatment;
-            } else {
-                treatment = defaultTreatment;
-            }
+        Set<PortNumber> copyIngressPorts = ImmutableSet.copyOf(ingressPorts);
+        Set<PortNumber> copyEgressPorts = ImmutableSet.copyOf(egressPorts);
+
+        inPorts.forEach(inport -> {
+            ForwardingInstructions instructions = this.createForwardingInstructions(intent,
+                                                                                    inport,
+                                                                                    outPorts,
+                                                                                    copyIngressPorts,
+                                                                                    copyEgressPorts);
 
             NextObjective nextObjective = DefaultNextObjective.builder()
                     .withId(flowObjectiveService.allocateNextId())
-                    .addTreatment(treatment)
+                    .addTreatment(instructions.treatment())
                     .withType(NextObjective.Type.SIMPLE)
                     .fromApp(appId)
                     .makePermanent().add();
             objectives.add(nextObjective);
 
             objectives.add(DefaultForwardingObjective.builder()
-                    .withSelector(selector)
+                    .withSelector(instructions.selector())
                     .nextStep(nextObjective.id())
                     .withPriority(intent.priority())
                     .fromApp(appId)
                     .makePermanent()
                     .withFlag(ForwardingObjective.Flag.SPECIFIC)
                     .add());
-        }
+            }
+        );
 
         return objectives;
     }
+
 }
