From 152b9414979975d65cc195ab405cbc4b1eadb1fb Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Mon, 15 Jul 2024 18:02:43 -0700 Subject: [PATCH 01/31] Update home page on sample app for 5.0 --- python-flask-directory-sync-example/app.py | 10 +++++----- python-flask-directory-sync-example/requirements.txt | 5 +++-- 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/python-flask-directory-sync-example/app.py b/python-flask-directory-sync-example/app.py index 4ed86ae..11b135c 100644 --- a/python-flask-directory-sync-example/app.py +++ b/python-flask-directory-sync-example/app.py @@ -38,13 +38,13 @@ def home(): directories = workos.client.directory_sync.list_directories( before=before, after=after, limit=5, order=None ) - before = directories["list_metadata"]["before"] - after = directories["list_metadata"]["after"] + + before = directories.list_metadata.before + after = directories.list_metadata.after return render_template( - "home.html", directories=directories["data"], before=before, after=after + "home.html", directories=directories.data, before=before, after=after ) - - + @app.route("/directory") def directory(): directory_id = request.args.get("id") diff --git a/python-flask-directory-sync-example/requirements.txt b/python-flask-directory-sync-example/requirements.txt index 9fd871d..9a06182 100644 --- a/python-flask-directory-sync-example/requirements.txt +++ b/python-flask-directory-sync-example/requirements.txt @@ -1,6 +1,7 @@ Flask>=1.1.2 -workos>=1.23.3 -urllib3==1.26.7 +../../SDKs/workos-python +workos>=4.0.0 +urllib3>=2 python-dotenv flask_socketio flask-lucide==0.2.0 \ No newline at end of file From 320abf00333e0cf79182a8276a7214e6eadd8906 Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Mon, 15 Jul 2024 19:11:33 -0700 Subject: [PATCH 02/31] Updates and fixes --- python-flask-directory-sync-example/app.py | 16 ++++++++++------ .../templates/home.html | 2 +- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/python-flask-directory-sync-example/app.py b/python-flask-directory-sync-example/app.py index 11b135c..d927c49 100644 --- a/python-flask-directory-sync-example/app.py +++ b/python-flask-directory-sync-example/app.py @@ -38,31 +38,34 @@ def home(): directories = workos.client.directory_sync.list_directories( before=before, after=after, limit=5, order=None ) - + directories.list_method before = directories.list_metadata.before after = directories.list_metadata.after return render_template( "home.html", directories=directories.data, before=before, after=after ) - + + @app.route("/directory") def directory(): directory_id = request.args.get("id") directory = workos.client.directory_sync.get_directory(directory_id) - return render_template("directory.html", directory=directory, id=directory["id"]) + return render_template("directory.html", directory=directory.model_dump(), id=directory.id) @app.route("/users") def directory_users(): directory_id = request.args.get("id") - users = workos.client.directory_sync.list_users(directory=directory_id, limit=100) + users = workos.client.directory_sync.list_users( + directory=directory_id, limit=100) return render_template("users.html", users=users) @app.route("/groups") def directory_groups(): directory_id = request.args.get("id") - groups = workos_client.directory_sync.list_groups(directory=directory_id, limit=100) + groups = workos_client.directory_sync.list_groups( + directory=directory_id, limit=100) return render_template("groups.html", groups=groups) @@ -73,7 +76,8 @@ def webhooks(): payload = request.get_data() sig_header = request.headers["WorkOS-Signature"] response = workos_client.webhooks.verify_event( - payload=payload, sig_header=sig_header, secret=os.getenv("WEBHOOKS_SECRET") + payload=payload, sig_header=sig_header, secret=os.getenv( + "WEBHOOKS_SECRET") ) message = json.dumps(response) diff --git a/python-flask-directory-sync-example/templates/home.html b/python-flask-directory-sync-example/templates/home.html index b789309..bd0cfa7 100644 --- a/python-flask-directory-sync-example/templates/home.html +++ b/python-flask-directory-sync-example/templates/home.html @@ -42,7 +42,7 @@

Select a Directory

{% for i in directories %} {{ i['name'] }} - {{ i['id'] }} + {{ i['id'] }} {{ lucide.icon('settings-2', stroke_width=1) }} {% endfor %} From 480d240a7cd1540237b20b70803c516b90487441 Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Tue, 16 Jul 2024 11:14:36 -0700 Subject: [PATCH 03/31] Add views for user and group details --- python-flask-directory-sync-example/app.py | 18 +++++++++ .../templates/group.html | 39 +++++++++++++++++++ .../templates/groups.html | 10 +++-- .../templates/user.html | 39 +++++++++++++++++++ .../templates/users.html | 12 +++--- 5 files changed, 109 insertions(+), 9 deletions(-) create mode 100644 python-flask-directory-sync-example/templates/group.html create mode 100644 python-flask-directory-sync-example/templates/user.html diff --git a/python-flask-directory-sync-example/app.py b/python-flask-directory-sync-example/app.py index d927c49..3fbcdfc 100644 --- a/python-flask-directory-sync-example/app.py +++ b/python-flask-directory-sync-example/app.py @@ -61,6 +61,15 @@ def directory_users(): return render_template("users.html", users=users) +@app.route("/user") +def directory_user(): + user_id = request.args.get("id") + user = workos.client.directory_sync.get_user( + user_id=user_id) + print(user.model_dump()) + return render_template("user.html", user=user.model_dump(), id=user_id) + + @app.route("/groups") def directory_groups(): directory_id = request.args.get("id") @@ -70,6 +79,15 @@ def directory_groups(): return render_template("groups.html", groups=groups) +@app.route("/group") +def directory_group(): + group_id = request.args.get("id") + group = workos_client.directory_sync.get_group( + group_id=group_id) + + return render_template("group.html", group=group.model_dump(), id=group_id) + + @app.route("/webhooks", methods=["GET", "POST"]) def webhooks(): if request.data: diff --git a/python-flask-directory-sync-example/templates/group.html b/python-flask-directory-sync-example/templates/group.html new file mode 100644 index 0000000..48e6809 --- /dev/null +++ b/python-flask-directory-sync-example/templates/group.html @@ -0,0 +1,39 @@ + + + + + + + +
+
+
+ workos logo +
+
+
+ + + + +
+
+
+ +
+
+

Group Details

+
+
+                        {{group|tojson_pretty}}
+                    
+
+
+
+
+ + + + \ No newline at end of file diff --git a/python-flask-directory-sync-example/templates/groups.html b/python-flask-directory-sync-example/templates/groups.html index b9adf91..93d7b44 100644 --- a/python-flask-directory-sync-example/templates/groups.html +++ b/python-flask-directory-sync-example/templates/groups.html @@ -4,7 +4,7 @@ - +
@@ -25,7 +25,7 @@
-
+

Groups Details

@@ -36,15 +36,17 @@

Groups Details

{% if groups['data']|length > 0 %}
- +
+ {% for group in groups['data'] %} - + + {% endfor %}
Name IDView Group
{{group['name']}}{{group['id']}}{{group['id']}}{{ lucide.icon('settings-2', stroke_width=1) }}
diff --git a/python-flask-directory-sync-example/templates/user.html b/python-flask-directory-sync-example/templates/user.html new file mode 100644 index 0000000..18e3833 --- /dev/null +++ b/python-flask-directory-sync-example/templates/user.html @@ -0,0 +1,39 @@ + + + + + + + +
+
+
+ workos logo +
+
+ +
+
+ +
+
+

User Details

+
+
+                        {{user|tojson_pretty}}
+                    
+
+
+
+
+ + + + \ No newline at end of file diff --git a/python-flask-directory-sync-example/templates/users.html b/python-flask-directory-sync-example/templates/users.html index 80d2678..a560933 100644 --- a/python-flask-directory-sync-example/templates/users.html +++ b/python-flask-directory-sync-example/templates/users.html @@ -4,7 +4,7 @@ - +
@@ -23,9 +23,9 @@
-
+
-

User Details

+

Directory Users

{% if users['data']|length > 0 %}
- +
+ {% for user in users['data'] %} - + + {% endfor %}
Name EmailView User
{{user['first_name']}} {{user['last_name']}}{{user['username']}}{{user['username']}}{{ lucide.icon('settings-2', stroke_width=1) }}
From e0e094d952c8c08b7457bdd885ced211e08ea9a9 Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Tue, 16 Jul 2024 11:52:50 -0700 Subject: [PATCH 04/31] API tweaks --- python-flask-directory-sync-example/app.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/python-flask-directory-sync-example/app.py b/python-flask-directory-sync-example/app.py index 3fbcdfc..61811dd 100644 --- a/python-flask-directory-sync-example/app.py +++ b/python-flask-directory-sync-example/app.py @@ -65,7 +65,7 @@ def directory_users(): def directory_user(): user_id = request.args.get("id") user = workos.client.directory_sync.get_user( - user_id=user_id) + user=user_id) print(user.model_dump()) return render_template("user.html", user=user.model_dump(), id=user_id) @@ -83,7 +83,7 @@ def directory_groups(): def directory_group(): group_id = request.args.get("id") group = workos_client.directory_sync.get_group( - group_id=group_id) + group=group_id) return render_template("group.html", group=group.model_dump(), id=group_id) From c92e84b0b7b1cd8cac1ba72100e160aa1525e262 Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Tue, 16 Jul 2024 14:33:06 -0700 Subject: [PATCH 05/31] Add guards to satisfy typing --- python-flask-directory-sync-example/app.py | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/python-flask-directory-sync-example/app.py b/python-flask-directory-sync-example/app.py index 61811dd..7911672 100644 --- a/python-flask-directory-sync-example/app.py +++ b/python-flask-directory-sync-example/app.py @@ -1,5 +1,6 @@ import os from flask import Flask, render_template, request +from typing_extensions import assert_never import workos from workos import client as workos_client from flask_socketio import SocketIO, emit @@ -16,7 +17,7 @@ socketio = SocketIO(app) if __name__ == "__main__": - socketio.run(app) + socketio.run(app) # type: ignore workos.api_key = os.getenv("WORKOS_API_KEY") workos.base_api_url = "http://localhost:5000/" if DEBUG else workos.base_api_url @@ -49,6 +50,8 @@ def home(): @app.route("/directory") def directory(): directory_id = request.args.get("id") + if not directory_id: + return "No directory ID provided", 400 directory = workos.client.directory_sync.get_directory(directory_id) return render_template("directory.html", directory=directory.model_dump(), id=directory.id) @@ -64,9 +67,11 @@ def directory_users(): @app.route("/user") def directory_user(): user_id = request.args.get("id") + if not user_id: + return "No user ID provided", 400 user = workos.client.directory_sync.get_user( user=user_id) - print(user.model_dump()) + return render_template("user.html", user=user.model_dump(), id=user_id) @@ -82,6 +87,9 @@ def directory_groups(): @app.route("/group") def directory_group(): group_id = request.args.get("id") + if not group_id: + return "No user ID provided", 400 + group = workos_client.directory_sync.get_group( group=group_id) From 358d7ab93a59f81dbbc18b24f368cd051fcca7de Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Thu, 1 Aug 2024 11:28:47 -0700 Subject: [PATCH 06/31] Add events page and fix up users --- python-flask-directory-sync-example/app.py | 72 ++++++++++---- .../static/home.css | 42 ++++++--- .../templates/events.html | 94 +++++++++++++++++++ .../templates/home.html | 37 ++++---- .../templates/user.html | 13 +-- 5 files changed, 197 insertions(+), 61 deletions(-) create mode 100644 python-flask-directory-sync-example/templates/events.html diff --git a/python-flask-directory-sync-example/app.py b/python-flask-directory-sync-example/app.py index 7911672..a0bf4fa 100644 --- a/python-flask-directory-sync-example/app.py +++ b/python-flask-directory-sync-example/app.py @@ -6,6 +6,12 @@ from flask_socketio import SocketIO, emit import json from flask_lucide import Lucide +import workos.directory_sync +import workos.resources +import workos.resources.directory_sync +import workos.typing +import workos.utils +import workos.utils.connection_types DEBUG = False @@ -37,9 +43,9 @@ def home(): before = request.args.get("before") after = request.args.get("after") directories = workos.client.directory_sync.list_directories( - before=before, after=after, limit=5, order=None + before=before, after=after, limit=5 ) - directories.list_method + before = directories.list_metadata.before after = directories.list_metadata.after return render_template( @@ -53,14 +59,16 @@ def directory(): if not directory_id: return "No directory ID provided", 400 directory = workos.client.directory_sync.get_directory(directory_id) - return render_template("directory.html", directory=directory.model_dump(), id=directory.id) + + return render_template( + "directory.html", directory=directory.model_dump(), id=directory.id + ) @app.route("/users") def directory_users(): directory_id = request.args.get("id") - users = workos.client.directory_sync.list_users( - directory=directory_id, limit=100) + users = workos.client.directory_sync.list_users(directory=directory_id, limit=100) return render_template("users.html", users=users) @@ -69,8 +77,7 @@ def directory_user(): user_id = request.args.get("id") if not user_id: return "No user ID provided", 400 - user = workos.client.directory_sync.get_user( - user=user_id) + user = workos.client.directory_sync.get_user(user=user_id) return render_template("user.html", user=user.model_dump(), id=user_id) @@ -78,8 +85,7 @@ def directory_user(): @app.route("/groups") def directory_groups(): directory_id = request.args.get("id") - groups = workos_client.directory_sync.list_groups( - directory=directory_id, limit=100) + groups = workos_client.directory_sync.list_groups(directory=directory_id, limit=100) return render_template("groups.html", groups=groups) @@ -90,24 +96,50 @@ def directory_group(): if not group_id: return "No user ID provided", 400 - group = workos_client.directory_sync.get_group( - group=group_id) + group = workos_client.directory_sync.get_group(group=group_id) return render_template("group.html", group=group.model_dump(), id=group_id) +@app.route("/events") +def events(): + after = request.args.get("after") + events = workos.client.events.list_events( + events=[ + "dsync.activated", + "dsync.deleted", + "dsync.group.created", + "dsync.group.deleted", + "dsync.group.updated", + "dsync.user.created", + "dsync.user.deleted", + "dsync.user.updated", + "dsync.group.user_added", + "dsync.group.user_removed", + ], + after=after, + limit=20, + ) + + after = events.list_metadata.after + events_data = list(map(lambda event: event.model_dump(), events.data)) + return render_template("events.html", events=events_data, after=after) + + @app.route("/webhooks", methods=["GET", "POST"]) def webhooks(): + signing_secret = os.getenv("WEBHOOKS_SECRET") if request.data: - payload = request.get_data() - sig_header = request.headers["WorkOS-Signature"] - response = workos_client.webhooks.verify_event( - payload=payload, sig_header=sig_header, secret=os.getenv( - "WEBHOOKS_SECRET") - ) - - message = json.dumps(response) - socketio.emit("webhook_received", message) + if signing_secret: + payload = request.get_data() + sig_header = request.headers["WorkOS-Signature"] + response = workos_client.webhooks.verify_event( + payload=payload, sig_header=sig_header, secret=signing_secret + ) + message = json.dumps(response.dict()) + socketio.emit("webhook_received", message) + else: + print("No signing secret configured") # Return a 200 to prevent retries based on validation return render_template("webhooks.html") diff --git a/python-flask-directory-sync-example/static/home.css b/python-flask-directory-sync-example/static/home.css index 82298a4..dc22ff8 100644 --- a/python-flask-directory-sync-example/static/home.css +++ b/python-flask-directory-sync-example/static/home.css @@ -133,6 +133,10 @@ h1 { bottom: 20%; } +.event_bodies { + position: inherit !important; +} + .logged_in_div_left h1 { color: #111111; font-size: 75px; @@ -143,14 +147,12 @@ h1 { } .home-hero-gradient { - background-image: linear-gradient( - 45deg, - #a163f1, - #6363f1 22%, - #3498ea 40%, - #40dfa3 67%, - rgba(64, 223, 163, 0) - ); + background-image: linear-gradient(45deg, + #a163f1, + #6363f1 22%, + #3498ea 40%, + #40dfa3 67%, + rgba(64, 223, 163, 0)); background-size: 150% 100%; background-repeat: no-repeat; -webkit-background-clip: text; @@ -192,14 +194,11 @@ div.text_box { overflow: scroll; border-width: 3px; border-style: solid; - border-image: linear-gradient( - #a163f1, + border-image: linear-gradient(#a163f1, #6363f1 22%, #3498ea 40%, #40dfa3 67%, - rgba(64, 223, 163, 0) - ) - 0 100%; + rgba(64, 223, 163, 0)) 0 100%; } .logged_in_nav { @@ -245,6 +244,10 @@ pre.prettyprint { border: none !important; } +pre.overflow_scroll { + overflow: scroll; +} + .text_input { border: 1px solid #555555; border-radius: 10px; @@ -354,6 +357,15 @@ th { padding: 15px 40px; } +tr.event_summary { + text-align: left; +} + +tr.selected_event { + font-weight: bold; + background-color: #ebebf2; +} + .width-75 { width: 75%; } @@ -418,6 +430,6 @@ th { border: none; } -#noborder > :first-child { +.prettyprinted> :first-child { display: none; -} +} \ No newline at end of file diff --git a/python-flask-directory-sync-example/templates/events.html b/python-flask-directory-sync-example/templates/events.html new file mode 100644 index 0000000..7347498 --- /dev/null +++ b/python-flask-directory-sync-example/templates/events.html @@ -0,0 +1,94 @@ + + + + + + + + +
+
+
+
+ + + + + + + + + {% for event in events %} + + + + + {% endfor %} + +
EventTime
{{ event['event'] }}{{ event['created_at'] }}
+
+ {% if after %} +
+ +
+ {% endif %} +
+
+
+
+ {% for event in events %} + + {% endfor %} +
+
+ + + + + \ No newline at end of file diff --git a/python-flask-directory-sync-example/templates/home.html b/python-flask-directory-sync-example/templates/home.html index bd0cfa7..86af246 100644 --- a/python-flask-directory-sync-example/templates/home.html +++ b/python-flask-directory-sync-example/templates/home.html @@ -5,7 +5,7 @@ - +
@@ -30,36 +30,37 @@

Select a Directory

Test Webhooks
- -
+ +
- - - + + + - {% for i in directories %} - + {% for i in directories %} + - - - - {% endfor %} -
OrganizationIDView SettingsOrganizationIDView Settings
{{ i['name'] }}{{ i['id'] }}{{ lucide.icon('settings-2', stroke_width=1) }}
-
+ {{ i['id'] }} + {{ + lucide.icon('settings-2', stroke_width=1) }} + + {% endfor %} + +
{% if after %} +
{% endif %} {% if before %}
-
- {% endif %} -
+
+ {% endif %} +
diff --git a/python-flask-directory-sync-example/templates/user.html b/python-flask-directory-sync-example/templates/user.html index 18e3833..769c620 100644 --- a/python-flask-directory-sync-example/templates/user.html +++ b/python-flask-directory-sync-example/templates/user.html @@ -21,15 +21,12 @@
- -
-
-

User Details

-
-
+        
+

User Details

+
+
                         {{user|tojson_pretty}}
-                    
-
+
From a78fcfcb2daaaa0e90ab16e85344345c96b8fe42 Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Thu, 1 Aug 2024 11:32:07 -0700 Subject: [PATCH 07/31] Make logo go back to home page --- .../templates/directory.html | 4 +-- .../templates/events.html | 2 +- .../templates/group.html | 4 +-- .../templates/groups.html | 25 ++++++++++--------- .../templates/home.html | 3 ++- .../templates/user.html | 2 +- .../templates/users.html | 25 ++++++++++--------- .../templates/webhooks.html | 2 +- 8 files changed, 35 insertions(+), 32 deletions(-) diff --git a/python-flask-directory-sync-example/templates/directory.html b/python-flask-directory-sync-example/templates/directory.html index fff8525..67d3f22 100644 --- a/python-flask-directory-sync-example/templates/directory.html +++ b/python-flask-directory-sync-example/templates/directory.html @@ -8,7 +8,7 @@
- workos logo + workos logo
@@ -21,7 +21,7 @@
- +

Directory Details

diff --git a/python-flask-directory-sync-example/templates/events.html b/python-flask-directory-sync-example/templates/events.html index 7347498..8d8b5e5 100644 --- a/python-flask-directory-sync-example/templates/events.html +++ b/python-flask-directory-sync-example/templates/events.html @@ -9,7 +9,7 @@
- workos logo + workos logo
diff --git a/python-flask-directory-sync-example/templates/group.html b/python-flask-directory-sync-example/templates/group.html index 48e6809..31f2d9c 100644 --- a/python-flask-directory-sync-example/templates/group.html +++ b/python-flask-directory-sync-example/templates/group.html @@ -8,7 +8,7 @@
- workos logo + workos logo
@@ -21,7 +21,7 @@
- +

Group Details

diff --git a/python-flask-directory-sync-example/templates/groups.html b/python-flask-directory-sync-example/templates/groups.html index 93d7b44..8e2b590 100644 --- a/python-flask-directory-sync-example/templates/groups.html +++ b/python-flask-directory-sync-example/templates/groups.html @@ -8,7 +8,7 @@
- workos logo + workos logo
@@ -21,7 +21,7 @@
- +
@@ -31,29 +31,30 @@

Groups Details

+ class='button button-sm button-outline'>Back
{% if groups['data']|length > 0 %}
- - - + + + - {% for group in groups['data'] %} - + {% for group in groups['data'] %} + - - - {% endfor %} + + + {% endfor %}
NameIDView GroupNameIDView Group
{{group['name']}} {{group['id']}}{{ lucide.icon('settings-2', stroke_width=1) }}
{{ + lucide.icon('settings-2', stroke_width=1) }}
{% else %}
No Groups Found
- {% endif %} + {% endif %}
diff --git a/python-flask-directory-sync-example/templates/home.html b/python-flask-directory-sync-example/templates/home.html index 86af246..6fd171f 100644 --- a/python-flask-directory-sync-example/templates/home.html +++ b/python-flask-directory-sync-example/templates/home.html @@ -9,7 +9,7 @@
- workos logo + workos logo
@@ -27,6 +27,7 @@

Select a Directory

diff --git a/python-flask-directory-sync-example/templates/user.html b/python-flask-directory-sync-example/templates/user.html index 769c620..6a3be83 100644 --- a/python-flask-directory-sync-example/templates/user.html +++ b/python-flask-directory-sync-example/templates/user.html @@ -8,7 +8,7 @@
- workos logo + workos logo
diff --git a/python-flask-directory-sync-example/templates/users.html b/python-flask-directory-sync-example/templates/users.html index a560933..ebafb41 100644 --- a/python-flask-directory-sync-example/templates/users.html +++ b/python-flask-directory-sync-example/templates/users.html @@ -8,7 +8,7 @@
- workos logo + workos logo
@@ -20,7 +20,7 @@
-
+
@@ -29,29 +29,30 @@

Directory Users

+ class='button button-sm button-outline'>Back
{% if users['data']|length > 0 %}
- - - + + + - {% for user in users['data'] %} - + {% for user in users['data'] %} + - - - {% endfor %} + + + {% endfor %}
NameEmailView UserNameEmailView User
{{user['first_name']}} {{user['last_name']}} {{user['username']}}{{ lucide.icon('settings-2', stroke_width=1) }}
{{ + lucide.icon('settings-2', stroke_width=1) }}
{% else %}
No Users Found
- {% endif %} + {% endif %}
diff --git a/python-flask-directory-sync-example/templates/webhooks.html b/python-flask-directory-sync-example/templates/webhooks.html index 0151baa..2d0b8f2 100644 --- a/python-flask-directory-sync-example/templates/webhooks.html +++ b/python-flask-directory-sync-example/templates/webhooks.html @@ -8,7 +8,7 @@
- workos logo + workos logo
From e4c08ebad48dc2c5880ddeb802303d150f963ba8 Mon Sep 17 00:00:00 2001 From: Peter Arzhintar Date: Thu, 1 Aug 2024 11:36:15 -0700 Subject: [PATCH 08/31] Handle no more events --- python-flask-directory-sync-example/templates/events.html | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/python-flask-directory-sync-example/templates/events.html b/python-flask-directory-sync-example/templates/events.html index 8d8b5e5..081e20f 100644 --- a/python-flask-directory-sync-example/templates/events.html +++ b/python-flask-directory-sync-example/templates/events.html @@ -22,6 +22,7 @@
+ {% if events|length > 0 %}
@@ -57,6 +58,9 @@ {% endfor %} + {% else %} +
No more events
+ {% endif %}