diff --git a/migrations/20170812041508_crate_owner_invitations/down.sql b/migrations/20170812041508_crate_owner_invitations/down.sql
new file mode 100644
index 00000000000..cfc741cbbb2
--- /dev/null
+++ b/migrations/20170812041508_crate_owner_invitations/down.sql
@@ -0,0 +1,3 @@
+DROP TRIGGER trigger_ensure_single_crate_owner_invitation ON crate_owner_invitations;
+DROP FUNCTION ensure_single_crate_owner_invitation();
+DROP TABLE crate_owner_invitations;
diff --git a/migrations/20170812041508_crate_owner_invitations/up.sql b/migrations/20170812041508_crate_owner_invitations/up.sql
new file mode 100644
index 00000000000..0561b0a50a3
--- /dev/null
+++ b/migrations/20170812041508_crate_owner_invitations/up.sql
@@ -0,0 +1,36 @@
+CREATE TABLE crate_owner_invitations (
+    id SERIAL PRIMARY KEY,
+    invited_user_id INTEGER NOT NULL REFERENCES users (id),
+    invited_by INTEGER NOT NULL REFERENCES users (id),
+    crate_id INTEGER NOT NULL REFERENCES crates (id) ON DELETE CASCADE,
+    status TEXT NOT NULL,
+    created TIMESTAMP NOT NULL DEFAULT now()
+);
+
+CREATE FUNCTION ensure_single_crate_owner_invitation() RETURNS trigger AS $$
+DECLARE
+    old_id INTEGER;
+BEGIN
+    IF TG_OP = 'UPDATE' THEN
+        old_id = OLD.id;
+    ELSE
+        old_id = -1;
+    END IF;
+
+    -- If a pending invitation already exists for this same invited user and crate
+    IF EXISTS (
+        SELECT 1 FROM crate_owner_invitations
+            WHERE id != old_id AND
+                  invited_user_id = NEW.invited_user_id AND
+                  crate_id = NEW.crate_id AND
+                  status = 'pending'
+    ) THEN
+        RAISE EXCEPTION 'cannot invite a user to the same crate more than once';
+    END IF;
+    RETURN NEW;
+END;
+$$ LANGUAGE plpgsql;
+
+CREATE TRIGGER trigger_ensure_single_crate_owner_invitation
+BEFORE INSERT OR UPDATE ON crate_owner_invitations
+FOR EACH ROW EXECUTE PROCEDURE ensure_single_crate_owner_invitation();
diff --git a/src/schema.rs b/src/schema.rs
index 2f25b813460..9c27ff3f32f 100644
--- a/src/schema.rs
+++ b/src/schema.rs
@@ -39,6 +39,17 @@ table! {
     }
 }
 
+table! {
+    crate_owner_invitations (id) {
+        id -> Int4,
+        invited_user_id -> Int4,
+        invited_by -> Int4,
+        crate_id -> Int4,
+        status -> Text,
+        created -> Timestamp,
+    }
+}
+
 table! {
     crate_owners (crate_id, owner_id, owner_kind) {
         crate_id -> Int4,