Fork me on GitHub
#clojure
<
2017-02-25
>
riz11:02:48

I'm gonna start with my first clojure web app today, and thought to follow this: http://clojure-doc.org/articles/tutorials/basic_web_development.html

danielsz11:02:50

riz: @riz After going through that exercise, you might want to have a look at https://github.com/danielsz/system-dependency-injection/tree/master. It has a similar stack, but it wires up everything together by leveraging some neat Clojure idioms.

riz11:02:01

Cool! I'll check it out

riz11:02:25

Am I right in assuming that the stack there is a kind of canonical in Clojure?

danielsz11:02:09

@riz Ring and Compojure are widely used in production. H2 not necessarily, but it is just a handy placeholder for a store because it ships as a jar. Hiccup is widely used too, but not essential.

riz12:02:22

I'm trying to get a quick and dirty timestamp, and (new java.util.Date) returns #inst "2017-02-25T12:43:15.284-00:00". How do I access that string?

riz12:02:57

I don't know what that format actually is so hard to google 😁

metametadata12:02:36

(.toString (new java.util.Date))

metametadata12:02:40

it will return something like "Sat Feb 25 14:50:28 EET 2017"

riz12:02:02

Yeah but I'd like it in the form thats between the quotes there

metametadata12:02:48

user=> (.toString (Instant/now)) "2017-02-25T12:53:35.660Z"

paulocuneo13:02:03

metametadata: or (str (new java.util.Date))

metametadata12:02:39

Instant is from java.time which should be preferred to java.util

riz12:02:31

I don't seem to have that by default, how can I include it?

metametadata12:02:56

in repl: (import [java.time Instant]) in (ns ...): (:import (java.time Instant))

riz13:02:10

Throws a ClassNotFoundException 😕

paulocuneo13:02:36

java.time is from java 8

riz13:02:33

Can't I read that somehow?

riz13:02:57

Maybe I'll just parse the (str (new java.util.Date))

riz13:02:00

Unix time could also be handy, can I get that easily from that?

paulocuneo13:02:26

riz: java: new java.util.Date().getTime() clojure: (.getTime (new java.util.Date))

riz13:02:04

Thanks! I think this will do for now

schmee13:02:26

riz if you’re going to anything non-trivial with dates I strongly recommend using https://github.com/clj-time/clj-time

riz13:02:55

At this point it's certainly trivial 😄

schmee13:02:53

well, pre-java8 java date handling is notoriously bad, so I’d just bite the bullet and use clj-time anyway 😄

schmee13:02:22

here’s how you get unix time for instance:

(c/to-long (t/date-time 1998 4 25))
=> 893462400000

rauh13:02:37

@schmee I wouldn't use clj-time for any new project. It's recommended not to use joda time anymore and instead use java.time.

schmee13:02:19

that might be true, but I’ve used clj-time a lot and it certainly gets the job done

schmee13:02:27

are the clojure wrappers for java.time any good?

rauh13:02:25

Frankly, I'm not a fan ob wrappers that add nothing but some convenience. java.time is already immutable so it's quite idiomatic for clojurians

rauh13:02:02

I don't mind the dot-syntax, it's also got great documentation. If I redo some things i just write a few convenience functions

schmee13:02:47

rauh those are the exact kind of functions I want someone else to write for me 😄

schmee13:02:35

usually I’d agree about wrappers, but IMO datetime stuff is pervasive enough to warrant an exception

rauh13:02:02

They were for my use-case. Other might need completely different functions. I used clj-time before but I'm much happier with just staying to java.time now.

schmee13:02:27

good thing Clojure makes it easy to use either one 🙂

metametadata13:02:05

I tried clojure.java-time wrapper but then quickly switched to bare java.time because Clojure lib didn't play well with Cursive IDE and I had to consult with JDK docs anyway to figure stuff out. The only minor drawback is dot-syntax.

seancorfield17:02:09

The clj-time team are planning a 2.0 version based on java.time at some point. It will mostly be a drop-in replacement for the 1.0 version but we're still nailing down how to handle the few differences that will be required.

dm317:02:25

I like clojure.java-time, but then I’m biased 🙂

danielsz18:02:26

Fressian barfs on a custom data reader tag. Do I need to write a custom handler?

ghadi18:02:23

fressian isn't cognizant of reader tags, only Java classes

ghadi18:02:02

tldr:yeah -- custom handler. I'm unclear if you're writing or reading

danielsz18:02:16

@ghadi Thanks. In the docs there is mention of any - TaggedObject. What does that refer to?

ghadi18:02:25

if you read something tagged (a fressian tag), that doesn't have a readhandler registered, you'll get a TaggedObject that has the {:tag and :value}. This is so that you can write it back without understanding what it was

ghadi18:02:34

"dumb conveyance"

ghadi18:02:47

Fressian intrisically knows how to write TaggedObjects

danielsz18:02:06

@ghadi Awesome. That was enlightening.

ghadi18:02:36

transit has the same feature i think.

dmh4322:02:48

I'd like to create a new type which is like a vector, except where (= coll (reverse coll)) is true. Is there a terse way to create a new type which defaults to the same protocol implementations of another type?

dmh4322:02:17

So far, I've just been using a vector and comparing them with a function i've written called branches-equal?. The issue with this is that functions such as distinct do not work as I'd like, since they do not use my custom compactor function

ag22:02:06

I feel completely stupid: If given two numbers: a and b, and one of them has to be positive: - they can't both contain positive value at the same time - they can't be both nil or zero at the same time How do I check for this?

ag22:02:19

I mean what’s the elegant way for such predicate?

ghadi22:02:43

ignoring the nil requirement, you're looking for xor essentially. (not= (pos? a) (pos? b))

ag22:02:26

@ghadi what if there’s more than two nums?

ghadi22:02:01

bounded or variable?

ag22:02:20

a b c,,, etc

ghadi22:02:37

so an indefinite list...

ghadi22:02:44

is a) exactly one allowed to be zero or b) just not all of them zero?

ag22:02:22

right, one of them HAS to have a positive value. only one

leroix22:02:10

@dmh43 I think you just define a new type that declares the same interfaces as a collection and only implements new functions where it needs to like https://github.com/reagent-project/reagent/blob/master/src/reagent/ratom.cljs#L121

leroix22:02:55

reagent’s RAtom seems like a good example

dmh4322:02:40

@leroix oh i hadnt realized that was the behavior. Thanks! Ill give that a shot

ghadi22:02:24

@ag

(fn [& nums]
  (let [{pos true neg false} (group-by pos? nums)]
    (= 1 (count pos))))

ag22:02:52

@ghadi whoa. cool thanks!

ghadi22:02:41

i kinda like the "group-by a predicate, then destructure the booleans" trick... sparingly

sgdread22:02:14

I like destructure trick

ghadi22:02:18

regarding nils - i recommend to eliminate them beforehand

tbaldridge22:02:58

group-by will return a map though @ghadi 😉

tbaldridge22:02:06

so it's something like (= 1 (count pos))

ghadi22:02:36

i accounted for the map, but not the list

tbaldridge22:02:43

ah right, it's a list