Hi! Implementing a type safe unix timestamp. I wan...
# announcements
i
Hi! Implementing a type safe unix timestamp. I want to make the constructor private (should only be initializable via factory methods) but the
value
used in it should be publicly readable:
Copy code
@Parcelize
data class UnixTime private constructor(value: Long) : Parcelable {

    companion object {
        fun fromValue(value: Long): UnixTime =
            UnixTime(value)

        fun minTimestamp(): UnixTime =
            UnixTime(0)

        fun now(): UnixTime =
            UnixTime(Date().time / 1000)
    }
}

fun UnixTime.debugString() =
    "$value, ${toDate()}"

fun UnixTime.toDate() =
    Date(value * 1000)
This doesn't compile, and has also a warning in
private
. How do I implement it correctly?
d
A data class' constructor is implicitly always public, because it can be accessed via the
copy
method. Why do you not want a public constructor, if all
fromValue
does is call it directly anyways?
k
I think the best would be to drop the
data
and just implement
equals
and
hashcode
i
@diesieben07 because I want to leave open the possibility to return an optional (e.g. if value is a negative number)
d
I don't see why the constructor needs to be private for that. The constructor can still check that the value is > 0 (or whatever other requirement you have).
You would need to do that anyways, if you have a data class, because of the generated
copy
method.
i
but the constructor can't return an optional
it would have to crash
d
Correct
Like I said, you have to do either that, or not make it a
data class
.
i
where do I find the default implementation of equals / hashcode? To just copy it
(for data classes I mean)
d
You can have IntelliJ generate it for you using Code > Generate
k
equals should just check if value is equal
oh yeah that works too
i
right, perfect
k
hashcode = value.hashcode. Should work
i
though oh my 😅
Copy code
override fun equals(other: Any?): Boolean {
    if (this === other) return true
    if (javaClass != other?.javaClass) return false
    other as UnixTime
    if (value != other.value) return false
    return true
}
k
huh, I thought kotlin had better equals
d
Its autogenerated code. It can be simplified, if you wnat to
i
probably like this?
Copy code
value == (other as? UnixTime)?.value
d
I'd do
return other is UnixTime && this.value == other.value
i
why, readability?
d
Yes, and also your code is not correct in case
value
is nullable.
i
oh because it would return
true
if
value
is null and
other
is null, right?
d
Yes
i
(not sure if
null == null
is true though)
ah ok
d
Well, or if
other
is not an instance of
UnixTime
i
right!
ok, great, thanks very much you both