Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add tenancies to room view #698

Merged
merged 3 commits into from
Mar 29, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 23 additions & 0 deletions tests/frontend/test_facilities.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from pycroft.model.facilities import Building, Room, Site
from pycroft.model.port import PatchPort
from web.blueprints.facilities.address import ADDRESS_ENTITIES
from web.blueprints.facilities.tables import RoomTenanciesRow
from tests import factories as f
from tests.factories import RoomFactory
from .assertions import TestClient
Expand Down Expand Up @@ -136,6 +137,28 @@ def test_building_level_rooms(
)


class TestRoomTenancies:
@pytest.fixture(scope="class")
def user(self, class_session):
return f.UserFactory(swdd_person_id="1")

@pytest.fixture(scope="class")
def room(self, class_session):
return f.RoomFactory(swdd_vo_suchname="1")

def test_room_tenancies_json(self, room, user, session, client):
resp = client.assert_url_ok(
url_for(
"facilities.room_tenancies_json",
room_id=room.id,
)
)
assert (items := resp.json.get("items"))
assert len(items) == 1
tenancy_row = RoomTenanciesRow.model_validate(items[0])
assert tenancy_row.inhabitant.title == user.name


class TestOvercrowdedRooms:
@pytest.fixture(scope="class", autouse=True)
def building(self, class_session) -> Building:
Expand Down
27 changes: 26 additions & 1 deletion web/blueprints/facilities/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@
from web.blueprints.helpers.log import format_room_log_entry
from web.blueprints.helpers.user import user_button
from web.blueprints.navigation import BlueprintNavigation
from web.table.table import TableResponse, LinkColResponse, BtnColResponse
from web.table.table import TableResponse, LinkColResponse, BtnColResponse, date_format
from .address import get_address_entity, address_entity_search_query
from .tables import (
BuildingLevelRoomTable,
Expand All @@ -70,9 +70,12 @@
BuildingLevelRoomRow,
PatchPortRow,
RoomOvercrowdedRow,
RoomTenanciesTable,
RoomTenanciesRow,
)
from ..helpers.exception import abort_on_error, ErrorHandlerMap
from ..helpers.log_tables import LogTableRow
from ...template_filters import date_filter

bp = Blueprint('facilities', __name__)
access = BlueprintAccess(bp, required_properties=['facilities_show'])
Expand Down Expand Up @@ -519,6 +522,11 @@ def room_show(room_id: int) -> ResponseReturnValue:
patch_port_table = PatchPortTable(data_url=url_for(".room_patchpanel_json", room_id=room.id),
room_id=room_id)

room_tenancies_table = RoomTenanciesTable(
data_url=url_for(".room_tenancies_json", room_id=room.id),
table_args={"data-search": "false"},
FestplattenSchnitzel marked this conversation as resolved.
Show resolved Hide resolved
)

return render_template(
"facilities/room_show.html",
page_title=f"Raum {room.short_name}",
Expand All @@ -535,6 +543,7 @@ def room_show(room_id: int) -> ResponseReturnValue:
],
room_log_table=room_log_table,
patch_port_table=patch_port_table,
room_tenancies_table=room_tenancies_table,
form=form,
)

Expand Down Expand Up @@ -600,6 +609,22 @@ def room_patchpanel_json(room_id: int) -> ResponseReturnValue:
).model_dump()


@bp.route("/room/<int:room_id>/tenancies/json")
def room_tenancies_json(room_id: int) -> ResponseReturnValue:
room = get_room_or_404(room_id)
return TableResponse[RoomTenanciesRow](
items=[
RoomTenanciesRow(
inhabitant=user_button(tenancy.user),
begins_at=date_format(tenancy.mietbeginn, formatter=date_filter),
ends_at=date_format(tenancy.mietende, formatter=date_filter),
status=tenancy.status.name,
)
for tenancy in room.tenancies
]
).model_dump()


@bp.route('/json/levels')
@access.require('facilities_show')
def json_levels() -> ResponseReturnValue:
Expand Down
20 changes: 20 additions & 0 deletions web/blueprints/facilities/tables.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
DateColumn,
LinkColResponse,
BtnColResponse,
DateColResponse,
)
from web.blueprints.infrastructure.tables import no_inf_change

Expand Down Expand Up @@ -104,3 +105,22 @@ class PatchPortRow(BaseModel):
switch_port: LinkColResponse | None = None
edit_link: BtnColResponse
delete_link: BtnColResponse


class RoomTenanciesTable(BootstrapTable):
_render_toolbar = False

inhabitants = BtnColumn("Bewohner")
begins_at = DateColumn("Von")
ends_at = DateColumn("Bis")
status = Column("Status")

class Meta:
table_args = {"data-sort-name": "begins_at"}
FestplattenSchnitzel marked this conversation as resolved.
Show resolved Hide resolved


class RoomTenanciesRow(BaseModel):
inhabitant: BtnColResponse | None = None
begins_at: DateColResponse
ends_at: DateColResponse
status: str
9 changes: 9 additions & 0 deletions web/templates/facilities/room_show.html
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,15 @@ <h3>Bewohner history</h3>
</div>
</section>

<section id="tenancies">
<h2 class="page-header">Mietverhältnisse</h2>
{% if room_tenancies_table %}
{{ room_tenancies_table.render("room_tenancies_table") }}
{% else %}
<span class="text-muted">Dieser Raum hat keine Mietverhältnisse</span>
{% endif %}
</section>

<section id="patchports">
<h2 class="page-header">Patchports</h2>
{% if ports %}
Expand Down
Loading