diff options
-rw-r--r-- | apps/notes/notebook_urls.py | 13 | ||||
-rw-r--r-- | apps/notes/notes_urls.py | 17 | ||||
-rw-r--r-- | apps/notes/tests/test_forms.py | 17 | ||||
-rw-r--r-- | apps/notes/tests/test_urls.py | 75 | ||||
-rw-r--r-- | apps/pages/tests/test_models.py | 36 | ||||
-rw-r--r-- | apps/pages/tests/test_views.py | 8 | ||||
-rw-r--r-- | design/templates/notes/partials/note_list.html | 16 | ||||
-rw-r--r-- | design/templates/notes/partials/note_sidebar.html | 13 | ||||
-rw-r--r-- | design/templates/pages/page.html | 5 |
9 files changed, 181 insertions, 19 deletions
diff --git a/apps/notes/notebook_urls.py b/apps/notes/notebook_urls.py new file mode 100644 index 0000000..b433d15 --- /dev/null +++ b/apps/notes/notebook_urls.py @@ -0,0 +1,13 @@ +from django.urls import path + +from .views import ( + NotebookListView, + NotebookDetailView, +) + +app_name = "notebooks" + +urlpatterns = [ + path(r'<slug>', NotebookDetailView.as_view(), name='detail',), + path(r'', NotebookListView.as_view(), name='list',), +] diff --git a/apps/notes/notes_urls.py b/apps/notes/notes_urls.py new file mode 100644 index 0000000..f2573ce --- /dev/null +++ b/apps/notes/notes_urls.py @@ -0,0 +1,17 @@ +from django.urls import path + +from .views import ( + NoteDetailView, + NoteCreateView, + NoteListView, + NoteTagView, +) + +app_name = "notes" + +urlpatterns = [ + path(r'create/', NoteCreateView.as_view(), name='create',), + path(r'<slug>/<pk>', NoteDetailView.as_view(), name='detail',), + path(r't/<slug>', NoteTagView.as_view(), name='tags',), + path(r'', NoteListView.as_view(), name='list',), +] diff --git a/apps/notes/tests/test_forms.py b/apps/notes/tests/test_forms.py new file mode 100644 index 0000000..a9b2a7d --- /dev/null +++ b/apps/notes/tests/test_forms.py @@ -0,0 +1,17 @@ +from django.test import TestCase +from notes.forms import NoteForm + + +class NoteFormTests(TestCase): + def test_forms(self): + form_data = { + 'title': 'My Note', + 'body_text': 'Body of the note', + 'body_html': '<p>Body of the note</p>', + 'body_qjson': '', + 'notebook': '', + 'url': '', + 'tags': 'three word tag, tag' + } + form = NoteForm(data=form_data) + self.assertTrue(form.is_valid()) diff --git a/apps/notes/tests/test_urls.py b/apps/notes/tests/test_urls.py new file mode 100644 index 0000000..e4fee57 --- /dev/null +++ b/apps/notes/tests/test_urls.py @@ -0,0 +1,75 @@ +from django.urls import reverse, resolve +from django.test import TestCase +from django.contrib import auth + +from mixer.backend.django import mixer + +from notes.models import Note + +User = auth.get_user_model() + + +class TestNotesURLs(TestCase): + """Test URL patterns for notes.""" + + def setUp(self): + self.user = mixer.blend(User, username='tpynchon') + self.note = Note.objects.create( + owner=self.user, + title="test note", + body_text="the body of the note", + url="https://luxagraf.net/", + tags="mine,cool site" + ) + self.note.save() + + def test_list_reverse(self): + """notes:list should reverse to /n/.""" + self.assertEqual(reverse('notes:list'), '/n/') + + def test_list_resolve(self): + """/n/ should resolve to notes:list.""" + self.assertEqual(resolve('/n/').view_name, 'notes:list') + + def test_detail_reverse(self): + """notes:detail should reverse to /n/slug/id""" + path = '/n/%s/%s' % (self.note.slug, self.note.pk) + self.assertEqual( + reverse('notes:detail', kwargs={'slug': self.note.slug, 'pk': self.note.pk}), path + ) + + def test_detail_resolve(self): + """/n/test-note/1 should resolve to notes:detail.""" + self.assertEqual(resolve('/n/test-note/1').view_name, 'notes:detail') + + def test_create_reverse(self): + """notes:create should reverse to /n/create/.""" + self.assertEqual(reverse('notes:create'), '/n/create/') + + def test_create_resolve(self): + """/n/create/ should resolve to notes:create""" + self.assertEqual( + resolve('/n/create/').view_name, + 'notes:create' + ) + + +class TestNotebooksURLs(TestCase): + """Test URL patterns for notebooks.""" + + def test_list_reverse(self): + """notebooks:list should reverse to /nb/.""" + self.assertEqual(reverse('notebooks:list'), '/nb/') + + def test_list_resolve(self): + """/n/ should resolve to notes:list.""" + self.assertEqual(resolve('/nb/').view_name, 'notebooks:list') + + def test_detail_reverse(self): + """notes:detail should reverse to /nb/slug""" + self.assertEqual(reverse('notebooks:detail', kwargs={'slug': 'test-notebook'}), '/nb/test-notebook') + + def test_detail_resolve(self): + """/n/test-note/1 should resolve to notes:detail.""" + self.assertEqual(resolve('/nb/test-notebook').view_name, 'notebooks:detail') + diff --git a/apps/pages/tests/test_models.py b/apps/pages/tests/test_models.py index f8de5c7..2722430 100644 --- a/apps/pages/tests/test_models.py +++ b/apps/pages/tests/test_models.py @@ -4,17 +4,33 @@ from pages.models import Page class PageModelTest(TestCase): - - def test_string_representation(self): - page = Page( + def setUp(self): + self.page = Page( title="Test Page", meta_description="The meta desc", body_markdown="the body of the page", ) - page.save() - self.assertEqual(str(page), "Test Page") - self.assertEqual(str(page.slug), "test-page") - self.assertEqual(str(page.body_markdown), "the body of the page") - self.assertEqual(str(page.body_html), "<p>the body of the page</p>") - self.assertEqual(str(page.meta_description), "The meta desc") - self.assertEqual(page.path, None) + self.page.save() + self.pathpage = Page( + title="Test Page", + meta_description="The meta desc", + body_markdown="the body of the page", + path="test-path", + ) + self.pathpage.save() + + def test_string_representation(self): + self.assertEqual(str(self.page), "Test Page") + self.assertEqual(str(self.page.slug), "test-page") + self.assertEqual(str(self.page.body_markdown), "the body of the page") + self.assertEqual(str(self.page.body_html), "<p>the body of the page</p>") + self.assertEqual(str(self.page.meta_description), "The meta desc") + self.assertEqual(self.page.path, None) + + def test_get_absolute_url(self): + """Absolute URL should return /page """ + self.assertEqual(str(self.page.get_absolute_url()), "/test-page") + + def test_path_get_absolute_url(self): + """Absolute URL with a path should return /path/page """ + self.assertEqual(str(self.pathpage.get_absolute_url()), "/test-path/test-page") diff --git a/apps/pages/tests/test_views.py b/apps/pages/tests/test_views.py index 42a91e4..c771a29 100644 --- a/apps/pages/tests/test_views.py +++ b/apps/pages/tests/test_views.py @@ -1,9 +1,9 @@ from django.test import RequestFactory, TestCase -from mixer.backend.django import mixer +from django.contrib import auth -from accounts.models import User from pages.models import Page -from pages.views import PageDetailView + +User = auth.get_user_model() class PageViewTest(TestCase): @@ -25,5 +25,3 @@ class PageViewTest(TestCase): def test_detail_view(self): response = self.client.get(self.page.get_absolute_url()) self.assertEqual(response.status_code, 200) - self.assertEqual(response.status_code, 200) - print(response.content) diff --git a/design/templates/notes/partials/note_list.html b/design/templates/notes/partials/note_list.html new file mode 100644 index 0000000..0c91b34 --- /dev/null +++ b/design/templates/notes/partials/note_list.html @@ -0,0 +1,16 @@ +<li {% if object.notebook and not hidecolor %}class="notebook-colored" style="border-left-color: {{object.notebook.color_rgb}};" {% endif %} > + <a href="{% url 'notes:detail' object.slug object.pk %}"> + <h4>{{object.title}}</h4> + <div class="note-preview">{{object.body_text|truncatewords:36}}</div> + </a> + <div class="flex-wrapper">{% if object.notebook and not hidenotebook %} + <div class="notebook"> + <a href="{% url 'notebooks:detail' object.slug %}"><span class="color-box" style="background-color: {{object.notebook.color_rgb}}"></span>{{object.notebook}}</a> + </div>{% endif %} + <div class="tags">tags: {% for tag in object.tags.all %} + <a href="{% url 'notes:tags' tag.slug %}"> + <span class="tag-wrapper" data-bg-color="#{{tag.color_hex}};" >{{tag}}</span> + </a> + {%endfor%}</div> + </div> + </li> diff --git a/design/templates/notes/partials/note_sidebar.html b/design/templates/notes/partials/note_sidebar.html new file mode 100644 index 0000000..1209fee --- /dev/null +++ b/design/templates/notes/partials/note_sidebar.html @@ -0,0 +1,13 @@ + <div class="svg-wrapper"><svg class="svg-icon-arrow"> + <svg viewBox="0 0 16 13" id="shape-double-arrow" width="100%" height="100%"><g stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" stroke-linecap="square"><g id="Showing-post-info" transform="translate(-297.000000, -105.000000)" stroke="currentColor"><g transform="translate(305.000000, 111.500000) scale(-1, 1) rotate(-180.000000) translate(-305.000000, -111.500000) translate(297.000000, 105.000000)"><path d="M2.20710678,6.5 L6.85355339,1.85355339 L7.20710678,1.5 L6.5,0.792893219 L6.14644661,1.14644661 L1.14644661,6.14644661 L1.05805826,6.23483496 L0.792893219,6.5 L1.14644661,6.85355339 L6.14644661,11.8535534 L6.5,12.2071068 L7.20710678,11.5 L6.85355339,11.1464466 L2.20710678,6.5 Z" id="Combined-Shape"></path><path d="M10.2071068,6.5 L14.8535534,1.85355339 L15.2071068,1.5 L14.5,0.792893219 L14.1464466,1.14644661 L9.14644661,6.14644661 L9.05805826,6.23483496 L8.79289322,6.5 L9.14644661,6.85355339 L14.1464466,11.8535534 L14.5,12.2071068 L15.2071068,11.5 L14.8535534,11.1464466 L10.2071068,6.5 Z" id="Combined-Shape"></path></g></g></g></svg> + </svg></div> + <div class=""> + <ul class="list-note-preview">{% for object in notes_list %} + <li> + <a href="{% url 'notes:detail' object.slug object.pk %}"> + <h4>{{object.title}}</h4> + <div class="note-preview">{{object.body_text|truncatewords:12}}</div> + </a> + </li> + {% endfor %}</ul> + </div> diff --git a/design/templates/pages/page.html b/design/templates/pages/page.html index 3feff75..9eccaff 100644 --- a/design/templates/pages/page.html +++ b/design/templates/pages/page.html @@ -1,6 +1,6 @@ {% extends 'base.html' %} {% block content %} -<main> +<main class="single-col"> <h1>{{page.title}}</h1> {{page.body_html|safe}} </main> @@ -22,9 +22,6 @@ novicell.overlay.create({ 'selector': trigger.getAttribute('data-element'), 'class': 'selector-overlay', - "onCreate": function() { console.log('created'); }, - "onLoaded": function() { console.log('loaded'); }, - "onDestroy": function() { console.log('Destroyed'); } }); }); {% endif %} |