diff --git a/utilsplugin2/src/org/openstreetmap/josm/plugins/utilsplugin2/UtilsPlugin2.java b/utilsplugin2/src/org/openstreetmap/josm/plugins/utilsplugin2/UtilsPlugin2.java
index 55da97e..80f2f13 100644
--- a/utilsplugin2/src/org/openstreetmap/josm/plugins/utilsplugin2/UtilsPlugin2.java
+++ b/utilsplugin2/src/org/openstreetmap/josm/plugins/utilsplugin2/UtilsPlugin2.java
@@ -13,6 +13,7 @@ import org.openstreetmap.josm.plugins.Plugin;
 import org.openstreetmap.josm.plugins.PluginInformation;
 import org.openstreetmap.josm.plugins.utilsplugin2.actions.AddIntersectionsAction;
 import org.openstreetmap.josm.plugins.utilsplugin2.actions.AlignWayNodesAction;
+import org.openstreetmap.josm.plugins.utilsplugin2.actions.CopyTagsAction;
 import org.openstreetmap.josm.plugins.utilsplugin2.actions.ExtractPointAction;
 import org.openstreetmap.josm.plugins.utilsplugin2.actions.PasteRelationsAction;
 import org.openstreetmap.josm.plugins.utilsplugin2.actions.SplitObjectAction;
@@ -47,7 +48,9 @@ import org.openstreetmap.josm.plugins.utilsplugin2.selection.UnselectNodesAction
 
 public class UtilsPlugin2 extends Plugin {
 
-	private static UtilsPlugin2 instance;
+    private static UtilsPlugin2 instance;
+
+    JMenuItem copyTags;
 
     JMenuItem unglueRelation;
     JMenuItem symmetry;
@@ -87,10 +90,13 @@ public class UtilsPlugin2 extends Plugin {
         super(info);
         instance = this;
 
+        JMenu editMenu = Main.main.menu.editMenu;
         JMenu toolsMenu = Main.main.menu.moreToolsMenu;
         JMenu dataMenu = Main.main.menu.dataMenu;
         JMenu selectionMenu = Main.main.menu.selectionMenu;
 
+        copyTags = MainMenu.addAfter(editMenu, new CopyTagsAction(), false, Main.main.menu.copy);
+
         addIntersections = MainMenu.add(toolsMenu, new AddIntersectionsAction());
         splitObject = MainMenu.add(toolsMenu, new SplitObjectAction());
         alignWayNodes = MainMenu.add(toolsMenu, new AlignWayNodesAction());
@@ -172,6 +178,6 @@ public class UtilsPlugin2 extends Plugin {
     }
 
     public static final UtilsPlugin2 getInstance() {
-    	return instance;
+        return instance;
     }
 }
diff --git a/utilsplugin2/src/org/openstreetmap/josm/plugins/utilsplugin2/actions/CopyTagsAction.java b/utilsplugin2/src/org/openstreetmap/josm/plugins/utilsplugin2/actions/CopyTagsAction.java
new file mode 100644
index 0000000..b851308
--- /dev/null
+++ b/utilsplugin2/src/org/openstreetmap/josm/plugins/utilsplugin2/actions/CopyTagsAction.java
@@ -0,0 +1,97 @@
+// License: GPL. For details, see LICENSE file.
+package org.openstreetmap.josm.plugins.utilsplugin2.actions;
+
+import static org.openstreetmap.josm.gui.help.HelpUtil.ht;
+import static org.openstreetmap.josm.tools.I18n.tr;
+
+import java.awt.event.ActionEvent;
+import java.awt.event.KeyEvent;
+
+import java.util.Collection;
+import java.util.Map;
+import java.util.Map.Entry;
+import java.util.Set;
+import java.util.TreeSet;
+
+import javax.swing.JOptionPane;
+
+import org.openstreetmap.josm.Main;
+import org.openstreetmap.josm.actions.JosmAction;
+import org.openstreetmap.josm.data.osm.OsmPrimitive;
+import org.openstreetmap.josm.data.osm.OsmPrimitiveType;
+import org.openstreetmap.josm.data.osm.Tag;
+import org.openstreetmap.josm.gui.layer.OsmDataLayer;
+import org.openstreetmap.josm.tools.Shortcut;
+import org.openstreetmap.josm.tools.Utils;
+
+/**
+ * Copy OSM primitives to clipboard in order to paste them, or their tags, somewhere else.
+ * @since 404
+ */
+public final class CopyTagsAction extends JosmAction {
+
+    /**
+     * Constructs a new {@code CopyTagsAction}.
+     */
+    public CopyTagsAction() {
+        super(tr("Copy Tags"), "copy",
+                tr("Copy all tags of selected objects to paste buffer."),
+                createShortcut(), true);
+        putValue("help", ht("/Action/CopyTags"));
+    }
+
+    public static Shortcut createShortcut() {
+        return Shortcut.registerShortcut("system:copytags", tr("Edit: {0}", tr("Copy Tags")), KeyEvent.CHAR_UNDEFINED, Shortcut.NONE);
+    }
+
+    @Override
+    public void actionPerformed(ActionEvent e) {
+        if (isEmptySelection()) return;
+        Collection<OsmPrimitive> selection = getCurrentDataSet().getSelected();
+        copy(getEditLayer(), selection);
+    }
+
+    /**
+     * Copies the tags of object to the clipboard. The output by this function
+     * looks similar to: key=value\nkey=value
+     * @param source The OSM data layer source
+     * @param primitives The OSM primitives to copy
+     */
+    public static void copy(OsmDataLayer source, Collection<OsmPrimitive> primitives) {
+        Set<String> values = new TreeSet<>();
+        for (OsmPrimitive p : primitives) {
+            for (Entry<String, String> kv : p.getKeys().entrySet()) {
+                values.add(new Tag(kv.getKey(), kv.getValue()).toString());
+            }
+        }
+        if (!values.isEmpty()) Utils.copyToClipboard(Utils.join("\n", values));
+    }
+
+    @Override
+    protected void updateEnabledState() {
+        if (getCurrentDataSet() == null) {
+            setEnabled(false);
+        } else {
+            updateEnabledState(getCurrentDataSet().getSelected());
+        }
+    }
+
+    @Override
+    protected void updateEnabledState(Collection<? extends OsmPrimitive> selection) {
+        setEnabled(selection != null && !selection.isEmpty());
+    }
+
+    private static boolean isEmptySelection() {
+        Collection<OsmPrimitive> sel = getCurrentDataSet().getSelected();
+        if (sel.isEmpty()) {
+            JOptionPane.showMessageDialog(
+                    Main.parent,
+                    tr("Please select something to copy."),
+                    tr("Information"),
+                    JOptionPane.INFORMATION_MESSAGE
+            );
+            return true;
+        }
+        return false;
+    }
+}
