mirror of
https://0xacab.org/sutty/sutty
synced 2024-11-16 21:46:22 +00:00
Merge branch 'issue-9361' into 'rails'
feat: implementar un servicio liviano de git-lfs #9361 See merge request sutty/sutty!129
This commit is contained in:
commit
2e95da98d4
3 changed files with 84 additions and 7 deletions
|
@ -4,11 +4,6 @@ module ActiveStorage
|
|||
class Service
|
||||
# Sube los archivos a cada repositorio y los agrega al LFS de su
|
||||
# repositorio git.
|
||||
#
|
||||
# @todo: Implementar LFS. No nos gusta mucho la idea porque duplica
|
||||
# el espacio en disco, pero es la única forma que tenemos (hasta que
|
||||
# implementemos IPFS) para poder transferir los archivos junto con el
|
||||
# sitio.
|
||||
class JekyllService < Service::DiskService
|
||||
# Genera un servicio para un sitio determinado
|
||||
#
|
||||
|
@ -27,7 +22,10 @@ module ActiveStorage
|
|||
# @param :checksum [String]
|
||||
def upload(key, io, checksum: nil, **)
|
||||
instrument :upload, key: key, checksum: checksum do
|
||||
IO.copy_stream(io, make_path_for(key)) unless exist?(key)
|
||||
unless exist?(key)
|
||||
IO.copy_stream(io, make_path_for(key))
|
||||
LfsObjectService.new(site: site, blob: blob_for(key)).process
|
||||
end
|
||||
ensure_integrity_of(key, checksum) if checksum
|
||||
end
|
||||
end
|
||||
|
@ -79,7 +77,7 @@ module ActiveStorage
|
|||
# @param :key [String]
|
||||
# @return [String]
|
||||
def filename_for(key)
|
||||
ActiveStorage::Blob.where(key: key).limit(1).pluck(:filename).first.tap do |filename|
|
||||
blob_for(key).filename.to_s.tap do |filename|
|
||||
raise ArgumentError, "Filename for key #{key} is blank" if filename.blank?
|
||||
end
|
||||
end
|
||||
|
@ -91,6 +89,15 @@ module ActiveStorage
|
|||
def path_for(key)
|
||||
File.join root, folder_for(key), filename_for(key)
|
||||
end
|
||||
|
||||
# @return [Site]
|
||||
def site
|
||||
@site ||= Site.find_by_name(name)
|
||||
end
|
||||
|
||||
def blob_for(key)
|
||||
ActiveStorage::Blob.find_by(key: key, service_name: name)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -117,6 +117,9 @@ class Site
|
|||
def commit(file:, usuarie:, message:, remove: false)
|
||||
file = [file] unless file.respond_to? :each
|
||||
|
||||
# Cargar el árbol actual
|
||||
rugged.index.read_tree rugged.head.target.tree
|
||||
|
||||
file.each do |f|
|
||||
remove ? rm(f) : add(f)
|
||||
end
|
||||
|
|
67
app/services/lfs_object_service.rb
Normal file
67
app/services/lfs_object_service.rb
Normal file
|
@ -0,0 +1,67 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
# Representa un objeto git LFS
|
||||
class LfsObjectService
|
||||
attr_reader :site, :blob
|
||||
|
||||
# @param :site [Site]
|
||||
# @param :blob [ActiveStorage::Blob]
|
||||
def initialize(site:, blob:)
|
||||
@site = site
|
||||
@blob = blob
|
||||
end
|
||||
|
||||
def process
|
||||
# Crear el directorio
|
||||
FileUtils.mkdir_p(File.dirname(object_path))
|
||||
|
||||
# Mover el archivo
|
||||
FileUtils.mv(path, object_path) unless File.exist? object_path
|
||||
|
||||
# Crear el pointer
|
||||
Site::Writer.new(site: site, file: path, content: pointer).save
|
||||
|
||||
# Commitear el pointer
|
||||
site.repository.commit(file: path, usuarie: author, message: File.basename(path))
|
||||
|
||||
# Eliminar el pointer
|
||||
FileUtils.rm(path)
|
||||
|
||||
# Hacer link duro del objeto al archivo
|
||||
FileUtils.ln(object_path, path)
|
||||
end
|
||||
|
||||
# @return [String]
|
||||
def path
|
||||
@path ||= blob.service.path_for(blob.key)
|
||||
end
|
||||
|
||||
# @return [String]
|
||||
def digest
|
||||
@digest ||= Digest::SHA256.file(path).hexdigest
|
||||
end
|
||||
|
||||
# @return [String]
|
||||
def object_path
|
||||
@object_path ||= File.join(site.path, '.git', 'lfs', 'objects', digest[0..1], digest[2..3], digest)
|
||||
end
|
||||
|
||||
# @return [Integer]
|
||||
def size
|
||||
@size ||= File.size(File.exist?(object_path) ? object_path : path)
|
||||
end
|
||||
|
||||
# @return [String]
|
||||
def pointer
|
||||
@pointer ||=
|
||||
<<~POINTER
|
||||
version https://git-lfs.github.com/spec/v1
|
||||
oid sha256:#{digest}
|
||||
size #{size}
|
||||
POINTER
|
||||
end
|
||||
|
||||
def author
|
||||
@author ||= GitAuthor.new email: "disk_service@#{Site.domain}", name: 'DiskService'
|
||||
end
|
||||
end
|
Loading…
Reference in a new issue