Clojurians
#precept
<
2018-03-12
>

This page is not created by, affiliated with, or supported by Slack Technologies, Inc.

alex-dixon20:03:12

Hey @amarjeet. Let me take a look

alex-dixon20:03:12

First thing that comes to mind is perhaps the user is already logged in? e.g. :loggedIn fact already exists

alex-dixon20:03:32

Looks like the view might not permit login when loggedIn is true though…

amarjeet20:03:54

no, :user/loggedIn fact is getting inserted for the first time

alex-dixon20:03:35

Can you clarify what data doesn’t exist and how you’re able to detect this?

alex-dixon20:03:43

I’m thinking you’re looking for this:

{:db/id (:id %)
                           :user/name (:name %)
                           :user/email (:email %)
                           :user/membershipId (:membershipId %)
                           :user/loggedIn true})
but I don’t see rules or subscrtptions that deal with these fields apart from authentication-successful which matches on :user/loggedIn

alex-dixon20:03:09

At a high level things should work as you described and I can’t see anything that would cause them not to

amarjeet20:03:23

I assumed it because when I fire the authentication-successful rule without [[?user :user/loggedIn true]] , the `:home-page gets rendered

amarjeet20:03:19

I am using these subs, also, the API is working - have checked them separetly

alex-dixon20:03:33

Hm. Well, a rule shouldn’t fire unless all its conditions are true. I might try changing [[?user :user/loggedIn true]] to

[?the-fact <- [?user :user/loggedIn true]]
and logging ?the-fact if you haven’t

amarjeet20:03:58

let me try this

alex-dixon20:03:59

Nice. This all looks great

alex-dixon20:03:13

I’d consider using insert! instead of insert-unconditional! wherever you can. It’s not clear whether you’re retracting facts elsewhere though (in which case insert-unconditional! is your friend)

alex-dixon20:03:13

I’m not confident that’s related to the problem you’re experiencing, just something I noticed

amarjeet20:03:51

So, its really strange that the rule with [[?user :user/loggedIn true]] alone is getting fired. But, its not getting fired when other conditions are put in - ex: it didn't fire with [?the-fact <- [?user :user/loggedIn true]] as well - I don't see anything printed in the console

amarjeet20:03:21

sorry, with [[?state :state/current-state :login-progress]] alone

amarjeet20:03:07

I dont see anything printed if i add [?the-fact <- [?user :user/loggedIn true]] condition

amarjeet20:03:27

and then log ?the-fact

amarjeet20:03:27

So, even if [?user :user/loggedIn true] doesn't exist, ?the-fact should log something right?

alex-dixon20:03:39

If I understand correctly, no. If the right hand side of the rule fires, then all the rule’s conditions are true.

amarjeet20:03:07

that means, the fact doesn't exist at the time of firing that rule

amarjeet20:03:27

does it have to do something with then?

alex-dixon20:03:41

?the-fact binds to the value of whole fact that matches [?user :user/loggedIn true]

alex-dixon20:03:08

Can you log ?user when the rule fires?

alex-dixon20:03:05

Because if the rule fires you should be able to log that as well as [?the-fact <- ...]

amarjeet20:03:19

let me check again

amarjeet20:03:44

No, its not getting logged - rule is not getting fired with user fact condition

amarjeet20:03:11

It seems like something with then

amarjeet20:03:12

when it inserts user fact at the time of api response

alex-dixon20:03:13

Try removing “true” from the condition. Maybe the else case of your if statement is evaluating?

amarjeet20:03:28

So, the steps are: when I click on login button, state changes to :login-progress, and api call happens, which should have inserted user fact - these to combined, should fire the rule in question

alex-dixon20:03:58

It could be a problem with then but I’m not sure how. The fullstack examples and other work I’m doing use the same pattern you’re using

amarjeet20:03:56

hmm, let me try removing the true condition

alex-dixon20:03:06

By doing that it should pick up a :user/loggedIn with anything in the value slot

amarjeet20:03:01

the rule fires with ?user value null

alex-dixon20:03:12

Kind of a side note but you can also see the state of the rules session at the end of each fire rules with @precept.state/store

amarjeet20:03:04

@precept.state/store this should help in debugging

alex-dixon20:03:17

Ok. So I’m guessing line 14 of your snippet is running instead of line 9

amarjeet20:03:54

actually no, I have tested with different set of rules - that is working fine. But, even with the 2nd condition, the ?user can't be null, because the fact is inserted with some id

alex-dixon21:03:50

Hm. Well, I’m guessing the reason the rule is firing now is because there’s a :user/loggedIn fact that has a value slot of false. That would explain why previously when the condition only matched on the value true the rule wasn’t firing

alex-dixon21:03:43

So you could try [?my-fact <- [?user :user/loggedIn]] and print the result of ?my-fact

amarjeet21:03:26

yes, it is firing with false as well

alex-dixon21:03:36

And hopefully it will be {:e nil :a :user/loggedIn :v false :t some number}. Otherwise I’m lost

alex-dixon21:03:16

Ok. Do you insert :user/loggedIn false anywhere else?

amarjeet21:03:02

I do get {:e nil :a :user/loggedIn :v false :t some number} kind of result

amarjeet21:03:06

its pretty weired

amarjeet21:03:25

:user/loggedIn is getting inserted only at the time of that api call

amarjeet21:03:04

The other strange thing is - if you see in the app return value, along with the :user/loggedIn false, it also inserted id, so why are we getting id as nil?

amarjeet21:03:16

in the api return value

alex-dixon21:03:16

(defn auth [email password]
  (GET "")
       {:params {:email email
                 :password password}
        :handler #(if (:login-status %)
                    (then {:db/id (:id %)
                           :user/name (:name %)
                           :user/email (:email %)
                           :user/membershipId (:membershipId %)
                           :user/loggedIn true})
                    (then {:db/id (:id %)
                           :user/loggedIn false}))
        :error-handler #(.log js/console %)}))
What’s the % / result you’re getting here?

amarjeet21:03:45

I printed %, and I got {:login-status true, :id 17592186045436, :name "Test User", :email "<mailto:[email protected]|[email protected]>", :membershipId "m0"}

alex-dixon21:03:12

Well…hm. What happens when you do:

#(if (:login-status %)
                    (then {:db/id (:id %)
                           :user/name (:name %)
                           :user/email (:email %)
                           :user/membershipId (:membershipId %)
                           :user/loggedIn true})
                    (then {:db/id (:id %)
                           :user/loggedIn false}))

alex-dixon21:03:29

Sorry one min

amarjeet21:03:25

So, i just tested with a hard-coded :db/id (ex: 2345), and now it returns :id as 2345, but with value false

amarjeet21:03:36

this is interesting :slightly_smiling_face:

alex-dixon21:03:02

Sorry. Basically I’m not convinced that’s the result :blush: it could be that then isn’t parsing Booleans in maps correctly

amarjeet21:03:36

hmm, i will just quickly use string and check

amarjeet21:03:10

doesn't look like its a boolean parsing error, I am getting same results with string as well

alex-dixon21:03:24

#(let [login-status (:login-status %)
          id (:id %)
          _ (println "Login status for id!" login-status id)
          (if login-status
            (let [facts [[id :user/name (:name %)]
                             [id :user/email (:email %)]
                             [id :user/membershipId (:membershipId %)]
                             [id :user/loggedIn true]]
                    (then facts))
           (let [facts [[id :user/loggedIn false]]
              (then facts))

alex-dixon21:03:47

Sorry for the formatting and probably wrong parens…

alex-dixon21:03:33

But if you could try that, it should show whether the response is what you expect and also circumvent any bugs pertaining to maps by using the vector format instead

amarjeet21:03:55

ites pretty weird, I am getting Login status for id! nil nil - so both login-status and id are nil

amarjeet21:03:46

I am changing my back-end response type for login-status to string. Just a sec

alex-dixon21:03:33

Is the response being parsed as EDN?

amarjeet21:03:28

This is my response map

amarjeet21:03:32

`{:login-status "true" :id user-id :name user-name :email stored-email :membershipId membershipId}`

amarjeet21:03:48

changing login-status to string didnt help

amarjeet21:03:50

same result

amarjeet21:03:30

its ring/response

alex-dixon21:03:19

Hm. Ok. Well, I think if you can get (:login-status) of the response to not be nil nil then everything else should work, with the rules the way you had originally

amarjeet21:03:07

yeah, i think I will try the api call with cljs-http once

alex-dixon21:03:44

Ok. Let me know how it works out or if I can be of any help

amarjeet21:03:48

holy cow :smile:

amarjeet21:03:56

it worked with cljs-http response

amarjeet21:03:25

yeah, super strange

amarjeet21:03:05

this is working

amarjeet21:03:37

Not sure what happened with Ajax

amarjeet21:03:13

Anyway, a big thanks to you - you spent over one n half an hr with me on this. Really really appreciate it :slightly_smiling_face:

amarjeet21:03:19

now I can sleep well

alex-dixon21:03:05

Of course. Thanks for sharing your code. Looks really good :slightly_smiling_face: