Repository: CiviWiki/OpenCiviWiki

Issue:
Can't Publish New Thread
I attempted to make a new thread on Civiwiki.org. I was able to create the content, but when I hit publish it throws a server error. 

![image](https://user-images.githubusercontent.com/30572202/57983784-ba53aa00-7a23-11e9-8e32-a036612b47b3.png)





Discussion:
@mdwest is there any error in your browser console (F12)? What is the server error? Please provide the texts.
*Note: It now says it is published when I hit publish, but I don't see it on the feed page yet. I'll update soon. 

-mw

This should now be fixed by Tomasz' PR, just merged into develop. Pleasr test again on civiwiki-dev.
@mdwest this may now be resolved by the recent deployment. Please verify.
Currently traveling, but I'll check asap.

-mw

On Sat, May 18, 2019, 1:52 AM Brylie Christopher Oxley <
notifications@github.com> wrote:

> @mdwest <https://github.com/mdwest> this may now be resolved by the
> recent deployment. Please verify.
>
> —
> You are receiving this because you were mentioned.
> Reply to this email directly, view it on GitHub
> <https://github.com/CiviWiki/OpenCiviWiki/issues/477?email_source=notifications&email_token=AHJH5KTO47EBZ5C56AFFQALPV67TDA5CNFSM4HMSQCQ2YY3PNVWWK3TUL52HS4DFVREXG43VMVBW63LNMVXHJKTDN5WW2ZLOORPWSZGODVWKS3I#issuecomment-493660525>,
> or mute the thread
> <https://github.com/notifications/unsubscribe-auth/AHJH5KRK2N2XCPZTMLLVZE3PV67TDANCNFSM4HMSQCQQ>
> .
>

@mdwest verified by email that this issue still affects the `dev` branch, despite us reverting to the previous version.

@mdwest please set up a Sentry account for CiviWiki, so we can track server errors.
OK, it looks like Sentry has been configured for CiviWiki, but I am unable to access the Sentry logs. @mdwest can you invite me to the CiviWiki Sentry team?
@brylie 
I have tested this issue. When I click on publish button, it occurs an server error, as following. 
Some icons can not be displaied either, e.g., keyboard_arrow_down.

![image](https://user-images.githubusercontent.com/23006864/57981870-fa407e80-7a6f-11e9-81a3-3cef8a570c02.png)


OK, thanks for reproducing @SunflowerPKU. Would you like to try and diagnose this error on the server-side? E.g. see if you can get a console log or other output for the specific server error.
I finally got the project to run locally again, and got the following error in the server console when trying to publish a  thread:

```
Editing thread
civiwiki-db | ERROR:  null value in column "title" violates not-null constraint
civiwiki-db | DETAIL:  Failing row contains (1, null, null, 2019-05-22 20:12:18.333649+00, 2019-05-22 20:19:40.302053+00, 1, null, 0, 0, 2, , null, null, t).
civiwiki-db | STATEMENT:  UPDATE "api_thread" SET "author_id" = 1, "category_id" = NULL, "title" = NULL, "summary" = NULL, "image" = '', "level" = NULL, "state" = NULL, "created" = '2019-05-22T20:12:18.333649+00:00'::timestamptz, "last_modified" = '2019-05-22T20:19:40.302053+00:00'::timestamptz, "is_draft" = true, "num_views" = 2, "num_civis" = 0, "num_solutions" = 0 WHERE "api_thread"."id" = 1
civiwiki-backend | null value in column "title" violates not-null constraint
civiwiki-backend | DETAIL:  Failing row contains (1, null, null, 2019-05-22 20:12:18.333649+00, 2019-05-22 20:19:40.302053+00, 1, null, 0, 0, 2, , null, null, t).
```

Resolving patch:
diff --git a/project/api/write.py b/project/api/write.py
--- a/project/api/write.py
+++ b/project/api/write.py
@@ -256,47 +256,50 @@ def deleteCivi(request):
 
 @login_required
 def editThread(request):
+    thread_id = request.POST.get("thread_id")
+    non_required_params = ["title", "summary", "category_id", "level", "state"]
+    is_draft = request.POST.get("is_draft", True)
 
-    thread_id = request.POST.get('thread_id')
-    title = request.POST.get('title')
-    summary = request.POST.get('summary')
-    category_id = request.POST.get('category_id')
-    level = request.POST.get('level')
-    state = request.POST.get('state')
     if not thread_id:
         return HttpResponseBadRequest(reason="Invalid Thread Reference")
-    else:
-        try:
-            req_edit_thread = Thread.objects.get(id=thread_id)
-
-            category_id = request.POST.get('category_id')
-            if request.user.username != req_edit_thread.author.user.username:
-                return HttpResponseBadRequest("No Edit Rights")
-
-            req_edit_thread.title = title
-            req_edit_thread.summary = summary
-            req_edit_thread.category_id = category_id
-            req_edit_thread.level = level
-            req_edit_thread.state = state
-            req_edit_thread.save()
-        except Exception as e:
-            return HttpResponseServerError(reason=str(e))
-
-        location = req_edit_thread.level if not req_edit_thread.state else dict(US_STATES).get(req_edit_thread.state)
-
-        return_data = {
-            'thread_id': thread_id,
-            'title': req_edit_thread.title,
-            'summary': req_edit_thread.summary,
-            "category": {
-                "id": req_edit_thread.category.id,
-                "name": req_edit_thread.category.name
-            },
-            "level": req_edit_thread.level,
-            "state": req_edit_thread.state if req_edit_thread.level == "state" else "",
-            "location": location,
-        }
-        return JsonResponse({'data': return_data})
+
+    if not is_draft:
+        Thread.objects.filter(id=thread_id).update(is_draft=False)
+
+        return JsonResponse({'data': "Success"})
+
+    try:
+        req_edit_thread = Thread.objects.get(id=thread_id)
+
+        if request.user.username != req_edit_thread.author.user.username:
+            return HttpResponseBadRequest("No Edit Rights")
+
+        # set remaining parameters from request
+        for param in non_required_params:
+            request_value = request.POST.get(param)
+
+            if request_value:
+                setattr(req_edit_thread, param, request_value)
+
+        req_edit_thread.save()
+    except Exception as e:
+        return HttpResponseServerError(reason=str(e))
+
+    location = req_edit_thread.level if not req_edit_thread.state else dict(US_STATES).get(req_edit_thread.state)
+
+    return_data = {
+        "thread_id": thread_id,
+        "title": req_edit_thread.title,
+        "summary": req_edit_thread.summary,
+        "category": {
+            "id": req_edit_thread.category.id,
+            "name": req_edit_thread.category.name
+        },
+        "level": req_edit_thread.level,
+        "state": req_edit_thread.state if req_edit_thread.level == "state" else "",
+        "location": location,
+    }
+    return JsonResponse({"data": return_data})
 
 
 


Test patch: