Django: Pagination without changing url? - python

I learned the pagination basics for Django from this link:
https://simpleisbetterthancomplex.com/tutorial/2016/08/03/how-to-paginate-with-django.html
However! the only problem I have is that I want to paginate without changing url.
By that, I mean I need to paginate a table while there are multiple tables in a html page.
How do i paginate only one table???
My code:
This is the basic structure of the html template:
...
<table class="uk-table uk-table-striped">
<tbody>
{% for post_status in post.statusPage %}
<tr>
<td>{{ post_status.status_time }}</td>
<td>{{ post_status.repost_count }}</td>
<td>{{ post_status.comment_count }}</td>
<td>{{ post_status.like_count }}</td>
</tr>
{% endfor %}
</tbody>
</table>
{% if post.statusPage.has_other_pages %}
<ul class="uk-pagination uk-flex-center" uk-margin>
{% if post.statusPage.has_previous %}
<li><span uk-pagination-previous></span></li>
{% else %}
<li><a><span uk-pagination-previous></span></a></li>
{% endif %}
{% for i in post.statusPage.paginator.page_range %}
{% if post.statusPage.number == i %}
<li class="uk-active"><span>{{ i }}</span></li>
{% else %}
<li>{{ i }}</li>
{% endif %}
{% endfor %}
{% if post.statusPage.has_next %}
<li><span uk-pagination-next></span></li>
{% else %}
<li><a><span uk-pagination-next></span></a></li>
{% endif %}
</ul>
{% endif %}
In side the template, there are multiple post objects
post
Each post has its own table and paginator:
post.statusPage
is the page object of the post.

Rather than building the pagination yourself and dealing with the complexity you're running into, consider using DataTables.
You can place multiple tables on a single view, and the pagination for each table is handled via javascript with no actual change in the URL. You can either insert the values into the table using standard django template tags, or you can build a simple API (using DRF or django's JSON libraries) to feed the tables via Ajax. This is a bit more advanced, but when you have a lot of data, it ensures you aren't sending it all to the user at once and hogging system memory.

I am not sure I know what you're trying to do, but it seems like your view returns a full set of tables, and you'd like the user to be able to view them one at a time, with a click in between, instead of scrolling down forever. You don't want to hit a different URL, so this needs to be handled in the client browser, and that means this is not a Django problem and hence not a Django solution. (Calling it pagination but also wanting it all to appear at the same URL and hence be the same web page is slightly confusing.)
The simplest way from where you are now might be toggling 'show-hide' html divs, that with a button created for each page. So each page is rendered but selectively presented. You'd have to modify the little script there to set all other pages to hidden.
I'm sorry I haven't got a better example for your particular situation. There are probably a bunch of more elegant javascript-heavy solutions out there, but I can't advise you on those.
If you are willing to send querystrings with a Get request for the next page, you could solve this entirely with Django, by creating links that include '?param=' type page numbers. The parameters can then be obtained from 'request.GET.getlist('param')' to return the right page. But if your view returns everything now, you might not want to get into generating and handling querystrings.

Related

Blending the rendering of DataTableView and a standard view in Django

I'm pretty new to django and have been experimenting with some of the code
I want to build a form that starts with a parent record, lists the children of that record, and then when I click on a child (or a button in the row of that child) shows the children under that in a datatableview object. phew It should look a little like this:
So the dataset is the primary object into the view, and the tables are a datatables filtered by the dataset id, which all works fine... but how do I get the {{ datatable }} to render in context?
The current view code is pretty basic - this is initially all just for display.
def datasetview(request, datasetid):
dataset = get_object_or_404(DataSet, pk=datasetid)
context = {
'dataset': dataset,
}
return render(request, 'data/dataset_view.html', context)
within the html template, I render the table list with:
{% for datatable in dataset.datatables.all %}
{% if not datatable.deleted %}
<tr>
<td class="p-1 align-middle">{{ datatable.tablename }}</td>
<td class="p-1 align-middle"><button type="button" class="btn btn-outline-primary" onclick="fill_attribute_table({{ datatable.datatableid }})">Edit</button></td>
</tr>
{% endif %}
{% endfor %}
I've been able to render the dataviewtable as a generic page using the demo code provided at pypi.org/project/django-datatable-view (that's how I produced the hacky screen image above) but have no idea how to blend the results here together or pass the datatableid that I can easily attach to the row of tables (the edit button currently throws up an alert with the relevant id...

Django Search And View more

I have search results in form of table. I want to add a detail page button which can send the id of the result to another function in view.py
so i can query it from database.
{% if sr %}
{% for k,j in sr %}
<tbody>
<tr>
<td>{{ k.id }}</td>
<td>{{ k.chromosome }}</td>
<td>{{ k.gene_id }} </td>
<td> view</td>
</tr>
</tbody>
{% endfor %}
{% endif %}
I want to send this k.id to another function
def detailed(request):
return render(request,"search/Detailed.html")
so I can again perform a query from database by this id
Since you didn't specify the version of django you're using, I'm going to assume it's 2.x. The only huge difference between that and more recent versions of 1.x is the urlpatterns. If you're using 1.11, just use the required regex's you need, as described in the docs. Either way, the principle is the same.
urls.py
urlpatterns = [
....
path('<int:some_id>/', views.detail_view, name='detail_view'),
# if django 1.11... you would use ([0-9]{4}) in place of the 'int', or for whatever max amount of numbers you'd want to capture... But I will continue for django 2.x.
]
views.py
def detail_view(request, some_id):
some_object = YourModel.objects.get(id=some_id)
return render(request, 'detail_template.html', {'some_object ': some_object})
detail_template.html
<p>{{ some_object.chromosome }}</p>
<p>{{ some_object.gene_id }}</p>
<p>View details</p>
Note that the url block above has some_object.id added to it as an argument AFTER the view it goes to in quotations. This is the easiest way.
You can also acheive the same thing with a model method by using the reverse('app_name:view_name', args=[arg_1, arg_2, etc) function, and then call the method with {{ some_object.your_method }}. But those arguments would all depend on what your url patterns and functions took.

How to switch off Description column in Django Rest Framework Documentation?

Is it possible to switch off Description column in Django Rest Framework Documentation? As you can see on the screenshot below there is a column Description. It is obvious what username and password mean, so I don't need to add more information, however empty cells don't look well. I would like to switch off it only for this method, because for instance in others I would like to have descriptions. Any ideas how can I do this?
There is no easy way to do this at the moment, since that 'Description' column is set at template level. See this template.
To be able to do this in a nicer way you need to customize rest_framework/docs/link.html, maybe have a template tag to check for a custom flag in here:
{% elif link.fields|with_location:'form' %}
<h4>Request Body</h4>
<p>The request body should be a <code>"{{ link.encoding }}"</code> encoded object, containing the following items.</p>
<table class="parameters table table-bordered table-striped">
<thead>
<tr><th>Parameter</th><th>Description</th></tr>
</thead>
<tbody>
{% for field in link.fields|with_location:'form' %}
<tr><td class="parameter-name"><code>{{ field.name }}</code>{% if field.required %} <span class="label label-warning">required</span>{% endif %}</td><td>{% if field.schema.description %}{{ field.schema.description }}{% endif %}</td></tr>
{% endfor %}
</tbody>
</table>
{% endif %}
But I think this is too much to consider just to have that column removed.

Flask redirect on select onchange

I'm a beginner to flask and I'm making a small web scraper app. What I've done so far has created a dropdown with a list of elements. Now I want to be able to render another page when the user selects a value from the list and I want to pass that value to the next page as well.
{% extends "base.html" %}
{% block content %}
<select id = "foo" onchange="">
{% for item in Citydata %}
<option value = {{ item.link }}> {{ item.name }} </option>
{% endfor %}
</select>
{% endblock %}
This makes the list and adds in all the links and values. I know that what should happen is that when an option is selected a new route is selected/used and a new template file is loaded. But I don't know how to do it.
If you are trying to do a form submission, follow colidyre's suggestion.
It seems to me, however, that you're looking to add a variable in your path, so you will need to use Flask's Variable Rules
It is unclear what item.link is, however if you have formatted that to be associated with an item's id such as /item/1, you could create an <a> tag like so:
{% for item in Citydata %}
{{ item.name }}
{% endfor %}
That would handle populating the href properly on the front-end, next you will need to set up the proper route on the server to handle the path:
#app.route('/item/<int:item_id>')
def item_route(item_id):
# do some stuff
NOTE: you don't have to create <a> tags, but it is a bit more straight forward than <option>. To stick with <option> you would just need to add some JavaScript client-side to call the back-end service based on the selected <option>'s value attribute instead.

integrating with existing html page django-page-cms

I have installed django-page-cms successfully i think. Like other cms, it is also for creating new pages. But I already have html pages in my project. How to integrate with that?
They want me to put place holder in html page, like:
{% load pages_tags %}
but I think this will bring the content from the already created page in admin
Can anyone tell me how to integrate with my existing pages?
First you need to create page in admin console. Then add the placeholder in your template
like what tutorial saying
{% get_page "news" as news_page %}
{% for new in news_page.get_children %}
<li>
{{ new.publication_date }}
{% show_content new body %}
{% endfor %}

Categories