Add Rails backend: accounts via magic link, server documents, sharing
The app becomes a Rails 8 application; the Vue frontend moves to app/frontend and is served through vite_rails. - Without an account documents stay in the browser (IndexedDB). Sign-in is by magic link or the 6-digit code from the same mail; afterwards local documents can be uploaded into the account. - Server documents (/d/<id>) with versioned saves and a single-editor lock per browser tab; others see them read-only and follow by polling. - Sharing via link (works without an account) and via e-mail invitation, roles viewer/editor; the owner manages links and people. - Store gains a read-only mode that blocks all content changes. - Solid Queue, Cache and Cable share the one PostgreSQL database. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,25 @@
|
||||
class DocumentMembership < ApplicationRecord
|
||||
belongs_to :document
|
||||
belongs_to :user
|
||||
belongs_to :share_link, optional: true
|
||||
|
||||
enum :role, { viewer: 0, editor: 1 }, validate: true
|
||||
enum :source, { invite: 0, link: 1 }, validate: true
|
||||
|
||||
# Grant access. An invitation is explicit: it sets exactly the invited role
|
||||
# and survives revoking any link. A link never weakens existing access and
|
||||
# never turns an invitation back into link-based access.
|
||||
def self.grant!(document:, user:, role:, source:, share_link: nil)
|
||||
return if document.owner_id == user.id
|
||||
m = find_or_initialize_by(document:, user:)
|
||||
if source.to_s == "invite"
|
||||
m.assign_attributes(role:, source: :invite, share_link: nil)
|
||||
elsif m.new_record?
|
||||
m.assign_attributes(role:, source: :link, share_link:)
|
||||
elsif m.link? && roles[role.to_s] > roles[m.role]
|
||||
m.assign_attributes(role:, share_link:)
|
||||
end
|
||||
m.save!
|
||||
m
|
||||
end
|
||||
end
|
||||
Reference in New Issue
Block a user