Skip to content

Commit 63343bc

Browse files
authored
feat: include origin server metadata in backup archive library (#430)
The origin server is passed in explicitly to avoid a dependency between Learning Core and edx-platform settings values.
1 parent c46668f commit 63343bc

File tree

5 files changed

+36
-10
lines changed

5 files changed

+36
-10
lines changed

openedx_learning/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,4 +2,4 @@
22
Open edX Learning ("Learning Core").
33
"""
44

5-
__version__ = "0.30.0"
5+
__version__ = "0.30.1"

openedx_learning/apps/authoring/backup_restore/api.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,15 +9,15 @@
99
from openedx_learning.apps.authoring.publishing.api import get_learning_package_by_key
1010

1111

12-
def create_zip_file(lp_key: str, path: str, user: UserType | None = None) -> None:
12+
def create_zip_file(lp_key: str, path: str, user: UserType | None = None, origin_server: str | None = None) -> None:
1313
"""
1414
Creates a dump zip file for the given learning package key at the given path.
1515
The zip file contains a TOML representation of the learning package and its contents.
1616
1717
Can throw a NotFoundError at get_learning_package_by_key
1818
"""
1919
learning_package = get_learning_package_by_key(lp_key)
20-
LearningPackageZipper(learning_package, user).create_zip(path)
20+
LearningPackageZipper(learning_package, user, origin_server).create_zip(path)
2121

2222

2323
def load_learning_package(path: str, key: str | None = None, user: UserType | None = None) -> dict:

openedx_learning/apps/authoring/backup_restore/management/commands/lp_dump.py

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,11 +32,18 @@ def add_arguments(self, parser):
3232
help='The username of the user performing the backup operation.',
3333
default=None
3434
)
35+
parser.add_argument(
36+
'--origin_server',
37+
type=str,
38+
help='The origin server for the backup operation.',
39+
default=None
40+
)
3541

3642
def handle(self, *args, **options):
3743
lp_key = options['lp_key']
3844
file_name = options['file_name']
3945
username = options['username']
46+
origin_server = options['origin_server']
4047
if not file_name.lower().endswith(".zip"):
4148
raise CommandError("Output file name must end with .zip")
4249
try:
@@ -45,7 +52,7 @@ def handle(self, *args, **options):
4552
if username:
4653
user = User.objects.get(username=username)
4754
start_time = time.time()
48-
create_zip_file(lp_key, file_name, user=user)
55+
create_zip_file(lp_key, file_name, user=user, origin_server=origin_server)
4956
elapsed = time.time() - start_time
5057
message = f'{lp_key} written to {file_name} (create_zip_file: {elapsed:.2f} seconds)'
5158
self.stdout.write(self.style.SUCCESS(message))

openedx_learning/apps/authoring/backup_restore/zipper.py

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -88,9 +88,22 @@ class LearningPackageZipper:
8888
A class to handle the zipping of learning content for backup and restore.
8989
"""
9090

91-
def __init__(self, learning_package: LearningPackage, user: UserType | None = None):
91+
def __init__(
92+
self,
93+
learning_package: LearningPackage,
94+
user: UserType | None = None,
95+
origin_server: str | None = None):
96+
"""
97+
Initialize the LearningPackageZipper.
98+
99+
Args:
100+
learning_package (LearningPackage): The learning package to zip.
101+
user (UserType | None): The user initiating the backup.
102+
origin_server (str | None): The origin server for the backup.
103+
"""
92104
self.learning_package = learning_package
93105
self.user = user
106+
self.origin_server = origin_server
94107
self.folders_already_created: set[Path] = set()
95108
self.entities_filenames_already_created: set[str] = set()
96109
self.utc_now = datetime.now(tz=timezone.utc)
@@ -269,7 +282,9 @@ def create_zip(self, path: str) -> None:
269282

270283
with zipfile.ZipFile(path, "w", compression=zipfile.ZIP_DEFLATED) as zipf:
271284
# Add the package.toml file
272-
package_toml_content: str = toml_learning_package(self.learning_package, self.utc_now, user=self.user)
285+
package_toml_content: str = toml_learning_package(
286+
self.learning_package, self.utc_now, user=self.user, origin_server=self.origin_server
287+
)
273288
self.add_file_to_zip(zipf, Path(TOML_PACKAGE_NAME), package_toml_content, self.learning_package.updated)
274289

275290
# Add the entities directory

tests/openedx_learning/apps/authoring/backup_restore/test_backup.py

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@
99
from django.contrib.auth import get_user_model
1010
from django.core.management import CommandError, call_command
1111
from django.db.models import QuerySet
12-
from django.test import override_settings
1312

1413
from openedx_learning.api import authoring as api
1514
from openedx_learning.api.authoring_models import Collection, Component, Content, LearningPackage, PublishableEntity
@@ -215,15 +214,18 @@ def check_zip_file_structure(self, zip_path: Path):
215214
for expected_path in expected_paths:
216215
self.assertIn(expected_path, zip_name_list)
217216

218-
@override_settings(CMS_BASE="http://cms.test", LMS_BASE="http://lms.test")
219217
def test_lp_dump_command(self):
220218
lp_key = self.learning_package.key
221219
file_name = f"{lp_key}.zip"
222220
try:
223221
out = StringIO()
224222

223+
origin_server = "http://origin.server"
224+
225225
# Call the management command to dump the learning package
226-
call_command("lp_dump", lp_key, file_name, username=self.user.username, stdout=out)
226+
call_command(
227+
"lp_dump", lp_key, file_name, username=self.user.username, origin_server=origin_server, stdout=out
228+
)
227229

228230
# Check that the zip file was created
229231
self.assertTrue(Path(file_name).exists())
@@ -244,6 +246,7 @@ def test_lp_dump_command(self):
244246
f'description = "{self.learning_package.description}"',
245247
'[meta]',
246248
'format_version = 1',
249+
'origin_server = "http://origin.server"',
247250
'created_at =',
248251
'created_by = "user"',
249252
'created_by_email = "[email protected]"',
@@ -301,7 +304,8 @@ def test_queries_n_plus_problem(self):
301304
1 query for all draft contents
302305
1 query for all published contents
303306
"""
304-
zipper = LearningPackageZipper(self.learning_package)
307+
dummy_path = "dummy/path"
308+
zipper = LearningPackageZipper(self.learning_package, dummy_path)
305309
entities = zipper.get_publishable_entities()
306310
with self.assertNumQueries(3):
307311
list(entities) # force evaluation

0 commit comments

Comments
 (0)