Why Cursor.use{...} does not compiles?


#1

This is a part of my code, in which I call method “use{…}” on a cursor from a query of database. There’s no any warn from the editor.

But when I build the project, it comes out:

What’s wrong? Or it is probably a bug?
(I’m using AndroidStudion 3.0 and Kotlin 1.1.60)


#2

This looks like a bug. The first option should match. A look at your gradle configuration may help. Also try a complete clean build (after you ensured you are using the latest versions)


#3

AFAIK Cursor didn’t implement Closeable until API level 16, so if you’re targeting lower API the use function is inapplicable to it.


#4

Well, it seems part of your answer is right.
When I copy the method use{..} and make it especailly for Cursor like this:

public inline fun <T : Cursor?, R> T.use(block: (T) -> R): R {
     var closed = false
     try {
         return block(this)
     } catch (e: Exception) {
         closed = true
         try {
             this?.close()
         } catch (closeException: Exception) {
         }
         throw e
     } finally {
         if (!closed) {
             this?.close()
         }
     }
 }

There is no any problem when I call my own method. It complies well.
Maybe somehow in compile time, Cursor really does not implements Closeable

But it seems is NOT the fault of api level. Such problem will occur even I set the minSdkVersion to 21 (when targetSdkVersion is 25).


#5

It’s probably best if you create a small project that demonstrates the problem that we could look at. The problem isn’t with the local code, so either a bug or a problem in your project configuration.


#6

Oh, I found it. It’s caused by the dependency of anko.

I created a small project as @pdvrieze says.


And I found that once I add the anko dependency, all the Kotlin codes are complied in a lower Android API level (haven’t recorgnized which level it is), ignoring the targetSdkVersion I set.
At this time, not only Corsor.use{..} goes wrong. Many of the apis that require higher API level can not be used in Kotlin code. (However, they can be used in Java code normally)
(Changing implementation to api dose not fix such problem.)

Whatever, changing anko dependency to level 0.10.3 can fix this problem.

But I have to say, adding an implementation should not change the compiling API level of my project! (especially only change the compliling API level of Kotlin code :confused: but not Java together)

Is this a bug of anko or something else?


#7

To overcome this you need to actually specify your Kotlin standard library in your dependencies. In that case Anko will not provide an ancient one. The explicit dependency on the library is always a good idea.