Coverage for src/lexigram/admin/controllers/resource/imports.py: 0%

20 statements  

« prev     ^ index     » next       coverage.py v7.15.4, created at 2026-08-24 23:18 +0800

1"""Import example/report downloads for the resource controller.""" 

2 

3from __future__ import annotations 

4 

5from typing import TYPE_CHECKING, Any 

6 

7from starlette.requests import Request 

8from starlette.responses import HTMLResponse, Response 

9 

10if TYPE_CHECKING: 

11 from lexigram.admin.controllers.resource import ResourceController 

12 

13 

14 

15class ResourceImportMixin: 

16 """Import example and report downloads.""" 

17 

18 def _find_import_action(self) -> Any: 

19 """Return the configured ImportAction, or None.""" 

20 return getattr(self, "_import_action", None) 

21 

22 async def import_example(self, request: Request) -> Response: 

23 """Serve the resource's import example CSV template as a download.""" 

24 action = self._find_import_action() 

25 if action is None or not action.example_csv(): 

26 return HTMLResponse( 

27 "<h1>Import not configured for this resource</h1>", 

28 status_code=404, 

29 ) 

30 return Response( 

31 content=action.example_csv(), 

32 media_type="text/csv", 

33 headers={ 

34 "Content-Disposition": ( 

35 f'attachment; filename="{action.example_filename}"' 

36 ) 

37 }, 

38 ) 

39 

40 async def import_report(self, request: Request) -> Response: 

41 """Serve a stored failed-import report as a CSV download.""" 

42 action = self._find_import_action() 

43 report_id = request.query_params.get("report_id", "") 

44 content = action.report_csv(report_id) if action else None 

45 if content is None: 

46 return HTMLResponse("<h1>Report not found</h1>", status_code=404) 

47 filename = action.report_filename(report_id) or "import-errors.csv" 

48 return Response( 

49 content=content, 

50 media_type="text/csv", 

51 headers={"Content-Disposition": f'attachment; filename="{filename}"'}, 

52 )