async def create_view( request: Request, resource: str = Path(...), resources=Depends(get_resources), model_resource: ModelResource = Depends(get_model_resource), ): inputs = await model_resource.get_inputs(request) context = { "request": request, "resources": resources, "resource_label": model_resource.label, "resource": resource, "inputs": inputs, "model_resource": model_resource, "page_title": model_resource.page_title, "page_pre_title": model_resource.page_pre_title, } try: return templates.TemplateResponse( f"{resource}/create.html", context=context, ) except TemplateNotFound: return templates.TemplateResponse( "create.html", context=context, )
async def update_view( request: Request, resource: str = Path(...), pk: int = Path(...), model_resource: ModelResource = Depends(get_model_resource), resources=Depends(get_resources), model=Depends(get_model), ): obj = await model.get(pk=pk) inputs = await model_resource.get_inputs(obj) context = { "request": request, "resources": resources, "resource_label": model_resource.label, "resource": resource, "inputs": inputs, "pk": pk, "model_resource": model_resource, "page_title": model_resource.page_title, "page_pre_title": model_resource.page_pre_title, } try: return templates.TemplateResponse( f"{resource}/update.html", context=context, ) except TemplateNotFound: return templates.TemplateResponse( "update.html", context=context, )
async def list_view( request: Request, model: Model = Depends(get_model), resources=Depends(get_resources), model_resource: ModelResource = Depends(get_model_resource), resource: str = Path(...), page_size: int = 10, page_num: int = 1, ): fields_name = model_resource.get_fields_name() fields_label = model_resource.get_fields_label() fields = model_resource.get_fields() qs = model.all() params, qs = await model_resource.resolve_query_params( request, dict(request.query_params), qs) filters = await model_resource.get_filters(request, params) total = await qs.count() if page_size: qs = qs.limit(page_size) else: page_size = model_resource.page_size qs = qs.offset((page_num - 1) * page_size) values = await qs.values(*fields_name) rendered_values, row_attributes, column_attributes, cell_attributes = await render_values( request, model_resource, fields, values) context = { "request": request, "resources": resources, "fields_label": fields_label, "fields": fields, "values": values, "row_attributes": row_attributes, "column_attributes": column_attributes, "cell_attributes": cell_attributes, "rendered_values": rendered_values, "filters": filters, "resource": resource, "model_resource": model_resource, "resource_label": model_resource.label, "page_size": page_size, "page_num": page_num, "total": total, "from": page_size * (page_num - 1) + 1, "to": page_size * page_num, "page_title": model_resource.page_title, "page_pre_title": model_resource.page_pre_title, } try: return templates.TemplateResponse( f"{resource}/list.html", context=context, ) except TemplateNotFound: return templates.TemplateResponse( "list.html", context=context, )
async def password( self, request: Request, old_password: str = Form(...), new_password: str = Form(...), re_new_password: str = Form(...), admin: AbstractAdmin = Depends(get_current_admin), resources=Depends(get_resources), ): error = None if not check_password(old_password, admin.password): error = _("old_password_error") elif new_password != re_new_password: error = _("new_password_different") if error: return templates.TemplateResponse( "password.html", context={ "request": request, "resources": resources, "error": error }, ) await self.update_password(admin, new_password) return await self.logout(request)
async def login(self, request: Request, redis: Redis = Depends(get_redis)): form = await request.form() username = form.get("username") password = form.get("password") remember_me = form.get("remember_me") admin = await self.admin_model.get_or_none(username=username) if not admin or not check_password(password, admin.password): return templates.TemplateResponse( self.template, status_code=HTTP_401_UNAUTHORIZED, context={ "request": request, "error": _("login_failed") }, ) response = RedirectResponse(url=request.app.admin_path, status_code=HTTP_303_SEE_OTHER) if remember_me == "on": expire = 3600 * 24 * 30 response.set_cookie("remember_me", "on") else: expire = 3600 response.delete_cookie("remember_me") token = uuid.uuid4().hex response.set_cookie( self.access_token, token, expires=expire, path=request.app.admin_path, httponly=True, ) await redis.set(constants.LOGIN_USER.format(token=token), admin.pk, expire=expire) return response
async def update( request: Request, resource: str = Path(...), pk: int = Path(...), model_resource: ModelResource = Depends(get_model_resource), resources=Depends(get_resources), model=Depends(get_model), ): form = await request.form() data, m2m_data = await model_resource.resolve_data(request, form) async with in_transaction() as conn: obj = (await model.filter( pk=pk).using_db(conn).select_for_update().get().prefetch_related( *model_resource.get_m2m_field())) await obj.update_from_dict(data).save(using_db=conn) for k, items in m2m_data.items(): m2m_obj = getattr(obj, k) await m2m_obj.clear() if items: await m2m_obj.add(*items) obj = (await model.filter(pk=pk).using_db(conn).get().prefetch_related( *model_resource.get_m2m_field())) inputs = await model_resource.get_inputs(obj) if "save" in form.keys(): context = { "request": request, "resources": resources, "resource_label": model_resource.label, "resource": resource, "model_resource": model_resource, "inputs": inputs, "pk": pk, "page_title": model_resource.page_title, "page_pre_title": model_resource.page_pre_title, } try: return templates.TemplateResponse( f"{resource}/update.html", context=context, ) except TemplateNotFound: return templates.TemplateResponse( "update.html", context=context, ) return redirect(request, "list_view", resource=resource)
async def update_password_view( request: Request, resources=Depends(get_resources), ): return templates.TemplateResponse( "password.html", context={ "request": request, "resources": resources, }, )
async def login_view( self, request: Request, ): return templates.TemplateResponse( self.template, context={ "request": request, "login_logo_url": self.login_logo_url, "login_title": self.login_title, }, )
async def password_view( self, request: Request, resources=Depends(get_resources), ): return templates.TemplateResponse( "providers/login/password.html", context={ "request": request, "resources": resources, }, )
async def home( request: Request, resources=Depends(get_resources), ): return templates.TemplateResponse( "home.html", context={ "request": request, "resources": resources, "resource_label": "Home", "page_pre_title": "home", "page_title": "Home page", }, )
async def home( request: Request, resources=Depends(get_resources), ): return templates.TemplateResponse( "dashboard.html", context={ "request": request, "resources": resources, "resource_label": "Dashboard", "page_pre_title": "overview", "page_title": "Dashboard", }, )
async def create( request: Request, resource: str = Path(...), resources=Depends(get_resources), model_resource: ModelResource = Depends(get_model_resource), model=Depends(get_model), ): inputs = await model_resource.get_inputs(request) form = await request.form() data, m2m_data = await model_resource.resolve_data(request, form) async with in_transaction() as conn: obj = await model.create(**data, using_db=conn) for k, items in m2m_data.items(): m2m_obj = getattr(obj, k) # type:ManyToManyRelation await m2m_obj.add(*items, using_db=conn) if "save" in form.keys(): return redirect(request, "list_view", resource=resource) context = { "request": request, "resources": resources, "resource_label": model_resource.label, "resource": resource, "inputs": inputs, "model_resource": model_resource, "page_title": model_resource.page_title, "page_pre_title": model_resource.page_pre_title, } try: return templates.TemplateResponse( f"{resource}/create.html", context=context, ) except TemplateNotFound: return templates.TemplateResponse( "create.html", context=context, )
async def home( request: Request, resources=Depends(get_resources), ): admin = request.state.admin if not admin: return RedirectResponse(url="/admin/login") return templates.TemplateResponse( "dashboard.html", context={ "request": request, "resources": resources, "resource_label": "Dashboard", "page_pre_title": "overview", "page_title": "Dashboard", }, )
async def init( self, request: Request, ): exists = await self.admin_model.all().limit(1).exists() if exists: return self.redirect_login(request) form = await request.form() password = form.get("password") confirm_password = form.get("confirm_password") username = form.get("username") if password != confirm_password: return templates.TemplateResponse( "init.html", context={ "request": request, "error": _("confirm_password_different") }, ) await self.create_user(username, password) return self.redirect_login(request)
async def unauthorized_error_exception(request: Request, exc: HTTPException): return templates.TemplateResponse( "errors/401.html", status_code=exc.status_code, context={"request": request} )
async def forbidden_error_exception(request: Request, exc: HTTPException): return templates.TemplateResponse("errors/403.html", status_code=exc.status_code, context={"request": request})
async def server_error_exception(request: Request, exc: HTTPException): return templates.TemplateResponse( "errors/500.html", status_code=HTTP_500_INTERNAL_SERVER_ERROR, context={"request": request}, )
async def init_view(self, request: Request): exists = await self.admin_model.all().limit(1).exists() if exists: return self.redirect_login(request) return templates.TemplateResponse("init.html", context={"request": request})