discourse/lib/theme_store/zip_importer.rb
Alan Guo Xiang Tan d2e4b32c87
DEV: Add support for uploading a theme from a directory in system tests (#23402)
Why this change?

Currently, we do not have an easy way to test themes and theme components
using Rails system tests. While we support QUnit acceptance tests for
themes and theme components, QUnit acceptance tests stubs out the server
and setting up the fixtures for server responses is difficult and can lead to a
frustrating experience. System tests on the other hand allow authors to
set up the test fixtures using our fabricator system which is much
easier to use.

What does this change do?

In order for us to allow authors to run system tests with their themes
installed, we are adding a `upload_theme` helper that is made available
when writing system tests. The `upload_theme` helper requires a single
`directory` parameter where `directory` is the directory of the theme
locally and returns a `Theme` record.
2023-09-12 07:38:47 +08:00

41 lines
1.1 KiB
Ruby

# frozen_string_literal: true
require "compression/engine"
class ThemeStore::ZipImporter < ThemeStore::BaseImporter
attr_reader :url
def initialize(filename, original_filename)
@temp_folder = "#{Pathname.new(Dir.tmpdir).realpath}/discourse_theme_#{SecureRandom.hex}"
@filename = filename
@original_filename = original_filename
end
def import!
FileUtils.mkdir(@temp_folder)
available_size = SiteSetting.decompressed_theme_max_file_size_mb
Compression::Engine
.engine_for(@original_filename)
.tap do |engine|
engine.decompress(@temp_folder, @filename, available_size)
strip_root_directory
end
rescue RuntimeError
raise RemoteTheme::ImportError, I18n.t("themes.import_error.unpack_failed")
rescue Compression::Zip::ExtractFailed
raise RemoteTheme::ImportError, I18n.t("themes.import_error.file_too_big")
end
def version
""
end
def strip_root_directory
root_files = Dir.glob("#{@temp_folder}/*")
if root_files.size == 1 && File.directory?(root_files[0])
FileUtils.mv(Dir.glob("#{@temp_folder}/*/*"), @temp_folder)
end
end
end