diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/AbstractMetaNetworkBuilder.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/AbstractMetaNetworkBuilder.java
new file mode 100644
index 0000000000000000000000000000000000000000..64ddbcfe48cca94fc70075fa967165cd528c562b
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/AbstractMetaNetworkBuilder.java
@@ -0,0 +1,209 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.*;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.collection.BioCollection;
+import lombok.SneakyThrows;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.*;
+import java.util.function.Function;
+import java.util.function.Supplier;
+import java.util.stream.Collectors;
+
+public abstract class AbstractMetaNetworkBuilder implements MultiNetworkBuilder{
+
+    BioCollection<BioNetwork> networks;
+    Map<BioCompartment, Map<BioNetwork, BioCollection<BioMetabolite>>> metaCompComposition;
+    MetaEntityFactory entityFactory;
+
+    Boolean keepGPR = false;
+    Boolean flush;
+    
+    public AbstractMetaNetworkBuilder(){
+        this.entityFactory= new DefaultMetaEntityFactory();
+    }
+
+    public AbstractMetaNetworkBuilder(MetaEntityFactory entityFactory){
+        this.entityFactory=entityFactory;
+    }
+
+    protected void addSharedCompartment(BioCompartment sc) {
+        metaCompComposition.put(sc,new HashMap<>());
+    }
+    protected void addSharedCompartment(BioCompartment sc, BioNetwork... bn) {
+        HashMap<BioNetwork, BioCollection<BioMetabolite>> map = Arrays.stream(bn).collect(Collectors.toMap(
+                x -> x,
+                x -> new BioCollection<BioMetabolite>(),
+                (prev, next) -> {prev.addAll(next);return prev;},
+                HashMap::new
+        ));
+        if(metaCompComposition.containsKey(sc)){
+            metaCompComposition.get(sc).putAll(map);
+        }else{
+            metaCompComposition.put(sc,map);
+        }
+    }
+
+    protected void fuseCompartmentIntoSharedCompartment(BioNetwork n, BioCompartment c, BioCompartment sc) {
+    //TODO
+    }
+
+    protected void bumpCompartmentIntoSharedCompartment(BioNetwork n, BioCompartment c, BioCompartment sc) {
+        Map<BioNetwork, BioCollection<BioMetabolite>> compartmentContent =  metaCompComposition.get(sc);
+        if(compartmentContent==null) throw new IllegalArgumentException("Shared Compartment not found");
+        BioCollection<BioMetabolite> sharedContent = compartmentContent.get(n);
+        if(compartmentContent==null) throw new IllegalArgumentException("SubNetwork not in shared compartment");
+        BioCollection<BioMetabolite> toShare = n.getMetabolitesView().stream()
+                .filter(x -> n.getCompartmentsOf(x).contains(c))
+                .collect(BioCollection::new,BioCollection::add,BioCollection::addAll);
+        sharedContent.addAll(toShare);
+    }
+
+    protected void exchangeWithSharedCompartment(BioNetwork n, BioMetabolite m, BioCompartment sc) {
+        //todo
+    }
+
+    protected void exchangeWithSharedCompartment(BioNetwork n, BioCollection<BioMetabolite> m, BioCompartment sc) {
+        //todo
+    }
+
+    @Override
+    public void add(BioNetwork bn) {
+        networks.add(bn);
+    }
+
+    @Override
+    public abstract void merge();
+
+    @Override
+    public abstract BioNetwork build();
+
+
+    void populateMetaNetwork(BioNetwork meta){
+
+        for(BioNetwork sub : networks){
+
+            Map<BioMetabolite,BioMetabolite> metaboliteConversion = new HashMap<>();
+            Map<BioCompartment,BioCompartment> compartmentConversion = new HashMap<>();
+            Map<BioReaction,BioReaction> reactionConversion = new HashMap<>();
+            Map<BioProtein,BioProtein> proteinConversion = new HashMap<>();
+            Map<BioEnzyme,BioEnzyme> enzymeConversion = new HashMap<>();
+            Map<BioGene,BioGene> geneConversion = new HashMap<>();
+
+            for(BioMetabolite e : sub.getMetabolitesView()){
+                BioMetabolite e2 = entityFactory.copy(e,sub);
+                meta.add(e2);
+                metaboliteConversion.put(e,e2);
+            }
+            for(BioCompartment c : sub.getCompartmentsView()){
+                BioCompartment c2 = entityFactory.copy(c,sub);
+                meta.add(c2);
+                compartmentConversion.put(c,c2);
+                c.getComponentsView().stream().
+                        filter((e) -> e.getClass().equals(BioMetabolite.class)).
+                        forEach((m) -> {
+                            BioMetabolite newMetabolite = metaboliteConversion.get(m);
+                            meta.affectToCompartment(c, newMetabolite);
+                        });
+            }
+
+            // Copy genes
+            if (keepGPR) {
+                //TODO case shared Genome
+                for (BioGene gene : sub.getGenesView()) {
+                    BioGene newGene = entityFactory.copy(gene,sub);
+                    meta.add(newGene);
+                    geneConversion.put(gene,newGene);
+                }
+                for (BioProtein protein : sub.getProteinsView()) {
+                    BioProtein newProtein = entityFactory.copy(protein,sub);
+                    meta.add(newProtein);
+                    proteinConversion.put(protein,newProtein);
+
+                    if (protein.getGene() != null) {
+                        BioGene newGene = geneConversion.get(protein.getGene());
+                        meta.affectGeneProduct(newProtein, newGene);
+                    }
+                }
+                for (BioEnzyme enzyme : sub.getEnzymesView()) {
+
+                    BioEnzyme newEnzyme = entityFactory.copy(enzyme,sub);
+                    meta.add(newEnzyme);
+                    enzymeConversion.put(enzyme,newEnzyme);
+
+                    BioCollection<BioEnzymeParticipant> participants = enzyme.getParticipantsView();
+
+                    for (BioEnzymeParticipant participant : participants) {
+                        Double quantity = participant.getQuantity();
+
+                        if (participant.getPhysicalEntity().getClass().equals(BioMetabolite.class)) {
+                            BioMetabolite metabolite = (BioMetabolite) participant.getPhysicalEntity();
+                            BioMetabolite newMetabolite = metaboliteConversion.get(metabolite);
+                            meta.affectSubUnit(newEnzyme, quantity, newMetabolite);
+                        } else if (participant.getPhysicalEntity().getClass().equals(BioProtein.class)) {
+                            BioProtein protein = (BioProtein) participant.getPhysicalEntity();
+                            BioProtein newProtein  = proteinConversion.get(protein);
+                            meta.affectSubUnit(newEnzyme, quantity, newProtein);
+                        }
+                    }
+                }
+            }
+
+            for (BioReaction r : sub.getReactionsView()) {
+
+                BioReaction newReaction = entityFactory.copy(r,sub);;
+                newReaction.setSpontaneous(r.isSpontaneous());
+                newReaction.setReversible(r.isReversible());
+                newReaction.setEcNumber(r.getEcNumber());
+
+                meta.add(newReaction);
+
+                // Copy lefts
+                for (BioReactant reactant : r.getLeftReactantsView()) {
+                    BioMetabolite newMetabolite = metaboliteConversion.get(reactant.getMetabolite());
+                    BioCompartment newCpt = compartmentConversion.get(reactant.getLocation().getId());
+                    Double sto = reactant.getQuantity();
+                    meta.affectLeft(newReaction, sto, newCpt, newMetabolite);
+                }
+
+                // Copy rights
+                for (BioReactant reactant : r.getRightReactantsView()) {
+                    BioMetabolite newMetabolite = metaboliteConversion.get(reactant.getMetabolite());
+                    BioCompartment newCpt = compartmentConversion.get(reactant.getLocation().getId());
+                    Double sto = reactant.getQuantity();
+                    meta.affectRight(newReaction, sto, newCpt, newMetabolite);
+                }
+
+                // Copy enzymes
+                if (keepGPR) {
+                    for (BioEnzyme enzyme : r.getEnzymesView()) {
+                        BioEnzyme newEnzyme = enzymeConversion.get(enzyme);
+                        meta.affectEnzyme(newReaction, newEnzyme);
+                    }
+                }
+            }
+
+            for (BioPathway pathway : sub.getPathwaysView()) {
+                BioPathway newPathway = entityFactory.copy(pathway,sub);
+                meta.add(newPathway);
+                // Add reactions into pathway
+                BioCollection<BioReaction> reactions = sub.getReactionsFromPathways(pathway);
+
+                for (BioReaction reaction : reactions) {
+                    BioReaction newReaction = reactionConversion.get(reaction);
+                    meta.affectToPathway(newPathway, newReaction);
+                }
+            }
+        }
+    }
+
+
+    void initSharedComp(BioNetwork meta){
+        for(Map.Entry<BioCompartment, Map<BioNetwork, BioCollection<BioMetabolite>>> compDescriptor : metaCompComposition.entrySet()){
+            meta.addCompartment(compDescriptor.getKey());
+            for(Map.Entry<BioNetwork, BioCollection<BioMetabolite>> content : compDescriptor.getValue().entrySet()){
+                meta.affectToCompartment(compDescriptor.getKey(),content.getValue());
+            }
+        }
+    }
+}
diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/DefaultMetaEntityFactory.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/DefaultMetaEntityFactory.java
new file mode 100644
index 0000000000000000000000000000000000000000..ce5227046b7c7cb0f504219ff9cf21c4d5cd6c2a
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/DefaultMetaEntityFactory.java
@@ -0,0 +1,42 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioEntity;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioNetwork;
+import lombok.SneakyThrows;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.function.BiFunction;
+import java.util.function.Function;
+
+public class DefaultMetaEntityFactory implements MetaEntityFactory {
+
+    public BiFunction<BioEntity, BioNetwork, String> idSupplier = (e,bn) -> {
+        return e.getId()+"_"+bn.getId();
+    };
+
+    public BiFunction<BioEntity, BioNetwork, String> getIdSupplier() {
+        return idSupplier;
+    }
+
+    public void setIdSupplier(BiFunction<BioEntity, BioNetwork, String> idSupplier) {
+        this.idSupplier = idSupplier;
+    }
+
+    @SneakyThrows
+    @Override
+    public <E extends BioEntity> E copy(E entity, BioNetwork source) {
+        return newEntityInstance(entity, this.idSupplier.apply(entity,source));
+    }
+
+    public static <E extends BioEntity> E newEntityInstance(E entity, String newId) throws NoSuchMethodException, InvocationTargetException, InstantiationException, IllegalAccessException {
+        E newEntity = (E) entity.getClass().getDeclaredConstructor(String.class).newInstance(newId);
+        newEntity.setName(entity.getName());
+        newEntity.setSynonyms(new ArrayList<>(entity.getSynonyms()));
+        newEntity.setComment(entity.getComment());
+        newEntity.setRefs(new HashMap<>(entity.getRefs()));
+        newEntity.setAttributes(new HashMap<>(entity.getAttributes()));
+        return newEntity;
+    }
+}
diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MetaEntityFactory.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MetaEntityFactory.java
new file mode 100644
index 0000000000000000000000000000000000000000..554d7b182f8656fa02db3580521a18b00d9cefe7
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MetaEntityFactory.java
@@ -0,0 +1,10 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioEntity;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioNetwork;
+
+public interface MetaEntityFactory {
+
+    public <E extends BioEntity> E copy(E entity, BioNetwork source);
+
+}
diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MetaNetworkBuilder.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MetaNetworkBuilder.java
new file mode 100644
index 0000000000000000000000000000000000000000..7af6a2b5f6ecb764142f90077aa56599df73fa41
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MetaNetworkBuilder.java
@@ -0,0 +1,45 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioCompartment;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioMetabolite;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioNetwork;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.collection.BioCollection;
+
+import java.util.UUID;
+
+public class MetaNetworkBuilder extends AbstractMetaNetworkBuilder implements MultiNetworkBuilder{
+
+
+    private BioCompartment medium;
+
+    public MetaNetworkBuilder(BioNetwork superNetwork){
+        setMedium();
+    }
+
+    private void setMedium(){
+        this.medium = new BioCompartment(UUID.randomUUID().toString(),"medium");
+        this.addSharedCompartment(medium);
+    }
+
+    @Override
+    public void add(BioNetwork bn) {
+        super.add(bn);
+        this.addSharedCompartment(medium,this.networks.stream().toArray(BioNetwork[]::new));
+    }
+
+    @Override
+    public void merge() {
+        //todo
+    }
+
+    public void exchangeWithMedium(BioNetwork n, BioMetabolite m){
+        this.exchangeWithSharedCompartment(n, m, medium);
+    };
+
+    @Override
+    public BioNetwork build() {
+        //todo
+        return null;
+    }
+
+}
diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MultiNetworkBuilder.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MultiNetworkBuilder.java
new file mode 100644
index 0000000000000000000000000000000000000000..c17e2cadc575dabf2fff0ccf5794af2409d96ec0
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MultiNetworkBuilder.java
@@ -0,0 +1,21 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioNetwork;
+
+public interface MultiNetworkBuilder {
+
+    /**
+     * add network into meta-network
+     * @param bn
+     */
+    public void add(BioNetwork bn);
+
+    public void merge();
+
+    /**
+     * create a new network which encompass all added networks
+     * @return
+     */
+    public BioNetwork build();
+
+}
diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MultiOrganNetworkBuilder.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MultiOrganNetworkBuilder.java
new file mode 100644
index 0000000000000000000000000000000000000000..ae4c1b699d22a8592769a0d657d6aa0d1be36322
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/MultiOrganNetworkBuilder.java
@@ -0,0 +1,57 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioCompartment;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioMetabolite;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioNetwork;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.collection.BioCollection;
+
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+public class MultiOrganNetworkBuilder extends AbstractMetaNetworkBuilder implements MultiNetworkBuilder{
+
+    @Override
+    public void merge() {
+        //TODO
+    }
+
+
+    @Override
+    public void addSharedCompartment(BioCompartment sc, BioNetwork... bn) {
+        super.addSharedCompartment(sc,bn);
+    }
+
+    @Override
+    public void fuseCompartmentIntoSharedCompartment(BioNetwork n, BioCompartment c, BioCompartment sc) {
+        super.fuseCompartmentIntoSharedCompartment(n,c,sc);
+    }
+
+    @Override
+    public void bumpCompartmentIntoSharedCompartment(BioNetwork n, BioCompartment c, BioCompartment sc) {
+        super.bumpCompartmentIntoSharedCompartment(n,c,sc);
+    }
+
+    @Override
+    public void exchangeWithSharedCompartment(BioNetwork n, BioMetabolite m, BioCompartment sc) {
+        super.exchangeWithSharedCompartment(n,m,sc);
+    }
+
+    @Override
+    public void exchangeWithSharedCompartment(BioNetwork n, BioCollection<BioMetabolite> m, BioCompartment sc) {
+        super.exchangeWithSharedCompartment(n,m,sc);
+    }
+
+    @Override
+    public BioNetwork build() {
+        //todo
+        //create empty meta network
+        BioNetwork meta = new BioNetwork();
+        //add each subnetwork content in dedicated compartment
+        this.populateMetaNetwork(meta);
+        //create shared compartment and the exchanged content
+        this.initSharedComp(meta);
+        return null;
+    }
+}
diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/NestedNetworkBuilder.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/NestedNetworkBuilder.java
new file mode 100644
index 0000000000000000000000000000000000000000..aeca0c100c4bfde965c364f4547f09d35205bb0f
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/NestedNetworkBuilder.java
@@ -0,0 +1,43 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioCompartment;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioMetabolite;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioNetwork;
+
+public class NestedNetworkBuilder extends AbstractMetaNetworkBuilder implements MultiNetworkBuilder{
+
+    private BioNetwork superNet;
+    private BioCompartment superNetComp;
+
+    public NestedNetworkBuilder(BioNetwork superNetwork){
+        setSuperNetwork(superNetwork);
+    }
+
+    private void setSuperNetwork(BioNetwork bn){
+        superNet=bn;
+        this.superNetComp = new BioCompartment(bn.getId());
+        this.addSharedCompartment(superNetComp,superNet);
+    }
+
+    @Override
+    public void add(BioNetwork bn) {
+        super.add(bn);
+        this.addSharedCompartment(superNetComp,this.networks.stream().toArray(BioNetwork[]::new));
+    }
+
+    @Override
+    public void merge() {
+        //todo
+    }
+
+    public void exchangeWithSuperNetwork(BioNetwork n, BioMetabolite m){
+        this.exchangeWithSharedCompartment(n, m, superNetComp);
+    };
+
+    @Override
+    public BioNetwork build() {
+        //todo
+        return null;
+    }
+
+}
diff --git a/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/PanNetworkBuilder.java b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/PanNetworkBuilder.java
new file mode 100644
index 0000000000000000000000000000000000000000..346f71cbfe702788ff6420621375320c99e86b07
--- /dev/null
+++ b/met4j-core/src/main/java/fr/inrae/toulouse/metexplore/met4j_core/biodata/multinetwork/PanNetworkBuilder.java
@@ -0,0 +1,23 @@
+package fr.inrae.toulouse.metexplore.met4j_core.biodata.multinetwork;
+
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioMetabolite;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.BioNetwork;
+import fr.inrae.toulouse.metexplore.met4j_core.biodata.collection.BioCollection;
+
+public class PanNetworkBuilder implements MultiNetworkBuilder {
+    @Override
+    public void add(BioNetwork bn) {
+        //todo
+    }
+
+    @Override
+    public void merge() {
+        //todo
+    }
+
+    @Override
+    public BioNetwork build() {
+        //todo
+        return null;
+    }
+}